The Battle for Wesnoth  1.19.5+dev
game_lua_kernel.hpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2009 - 2024
3  by Guillaume Melquiond <guillaume.melquiond@gmail.com>
4  Part of the Battle for Wesnoth Project https://www.wesnoth.org/
5 
6  This program is free software; you can redistribute it and/or modify
7  it under the terms of the GNU General Public License as published by
8  the Free Software Foundation; either version 2 of the License, or
9  (at your option) any later version.
10  This program is distributed in the hope that it will be useful,
11  but WITHOUT ANY WARRANTY.
12 
13  See the COPYING file for more details.
14 */
15 
16 #pragma once
17 
18 #include "scripting/lua_kernel_base.hpp" // for lua_kernel_base
19 
20 #include "game_events/action_wml.hpp" // for wml_action, etc
21 
22 #include <stack>
23 #include <string> // for string
24 
25 class game_config_view;
26 class unit;
27 class vconfig;
28 namespace ai { class engine_lua; }
29 namespace ai { class lua_ai_action_handler; }
30 namespace ai { class lua_ai_context; }
31 
32 class game_display;
33 class game_state;
34 class game_board;
35 class unit_map;
36 class gamemap;
37 class team;
38 class game_data;
39 class tod_manager;
40 class play_controller;
41 class reports;
42 
43 struct map_location;
44 typedef int (*lua_CFunction) (lua_State *L);
45 
47 {
52 
53  // Private functions to ease access to parts of game_state
54  unit_map & units();
55  game_data & gamedata();
56  tod_manager & tod_man();
57 
60  bool has_preloaded_ = false;
61 
62  std::stack<game_events::queued_event const * > queued_events_;
63 
65 
67  static std::vector<config> preload_scripts;
69 
70  friend class game_config_manager; // to allow it to call extract_preload_scripts
71  friend struct current_tag;
72  friend struct scenario_tag;
73  friend struct schedule_tag;
74  friend struct game_config_glk_tag;
75 
76  // Private lua callbacks
77  int intf_allow_end_turn(lua_State *);
78  int intf_allow_undo(lua_State *);
79  int intf_cancel_action(lua_State *);
80  int intf_add_time_area(lua_State *);
81  int intf_remove_time_area(lua_State *);
82  int intf_get_time_area(lua_State *);
83  int intf_animate_unit(lua_State *);
84  int intf_gamestate_inspector(lua_State *);
85  int impl_run_animation(lua_State *);
86  int intf_create_animator(lua_State *);
87  int intf_get_unit(lua_State *);
88  int intf_get_units(lua_State *);
89  int intf_get_displayed_unit(lua_State*);
90  int intf_match_unit(lua_State *L);
91  int intf_get_recall_units(lua_State *L);
92  int intf_get_variable(lua_State *L);
93  int intf_set_variable(lua_State *L);
94  int intf_highlight_hex(lua_State *L);
95  int intf_is_enemy(lua_State *L);
96  int intf_unit_ability(lua_State *L);
97  int intf_view_locked(lua_State *L);
98  int intf_lock_view(lua_State *L);
99  int impl_get_terrain_info(lua_State *L);
100  int impl_get_terrain_list(lua_State *L);
101  template<bool consider_illuminates>
102  int intf_get_time_of_day(lua_State *L);
103  int impl_schedule_get(lua_State *L);
104  int impl_schedule_len(lua_State *L);
105  void luaW_push_schedule(lua_State* L, int area_index);
106  int intf_get_village_owner(lua_State *L);
107  int intf_set_village_owner(lua_State *L);
108  int intf_get_mouseover_tile(lua_State *L);
109  int intf_get_selected_tile(lua_State *L);
110  int impl_scenario_get(lua_State *L);
111  int impl_scenario_set(lua_State *L);
112  int impl_scenario_dir(lua_State *L);
113  int impl_current_get(lua_State *L);
114  int impl_current_dir(lua_State *L);
115  int intf_clear_messages(lua_State*);
116  int impl_end_level_data_set(lua_State*);
117  int intf_end_turn(lua_State*);
118  int intf_find_cost_map(lua_State *L);
119  int intf_find_path(lua_State *L);
120  int intf_find_reach(lua_State *L);
121  int intf_find_vision_range(lua_State *L);
122  int intf_heal_unit(lua_State *L);
123  int intf_message(lua_State *L);
124  int intf_play_sound(lua_State *L);
125  int intf_set_achievement(lua_State *L);
126  int intf_has_achievement(lua_State *L);
127  int intf_has_sub_achievement(lua_State *L);
128  int intf_get_achievement(lua_State *L);
129  int intf_progress_achievement(lua_State *L);
130  int intf_set_sub_achievement(lua_State *L);
131  int intf_set_floating_label(lua_State* L, bool spawn);
132  int intf_remove_floating_label(lua_State* L);
133  int intf_move_floating_label(lua_State* L);
134  void put_unit_helper(const map_location& loc);
135  int intf_put_unit(lua_State *L);
136  int intf_erase_unit(lua_State *L);
137  int intf_put_recall_unit(lua_State *L);
138  int intf_extract_unit(lua_State *L);
139  int intf_find_vacant_tile(lua_State *L);
140  int intf_float_label(lua_State *L);
141  int intf_clear_menu_item(lua_State *L);
142  int intf_create_side(lua_State *L);
143  int intf_set_menu_item(lua_State *L);
144  int intf_toggle_shroud(lua_State *L, bool place_shroud);
145  int intf_override_shroud(lua_State *L);
146  int intf_simulate_combat(lua_State *L);
147  int intf_scroll_to_tile(lua_State *L);
148  int intf_select_unit(lua_State *L);
149  int intf_deselect_hex(lua_State *L);
150  int intf_is_skipping_messages(lua_State *L);
151  int intf_skip_messages(lua_State *L);
152  int intf_get_locations(lua_State *L);
153  int intf_match_location(lua_State *L);
154  int intf_match_side(lua_State *L);
155  int intf_set_side_id(lua_State *L);
156  int intf_modify_ai_wml(lua_State *L);
157  int intf_get_sides(lua_State* L);
158  int intf_get_side(lua_State* L);
159  int intf_add_tile_overlay(lua_State *L);
160  int intf_remove_tile_overlay(lua_State *L);
161  template<bool is_menu_item>
162  int intf_add_event_simple(lua_State* L);
163  int intf_add_event_wml(lua_State* L);
164  int intf_add_event(lua_State *L);
165  int intf_add_undo_actions(lua_State *L);
166  int cfun_undoable_event(lua_State *L);
167  int intf_remove_event(lua_State *L);
168  int intf_color_adjust(lua_State *L);
169  int intf_get_color_adjust(lua_State *L);
170  int intf_screen_fade(lua_State *L);
171  int intf_delay(lua_State *L);
172  int intf_add_label(lua_State *L);
173  int intf_remove_label(lua_State *L);
174  int intf_get_label(lua_State* L);
175  int intf_redraw(lua_State *L);
176  int intf_replace_schedule(lua_State *l);
177  int impl_schedule_set(lua_State *L);
178  int impl_schedule_dir(lua_State *L);
179  int intf_scroll(lua_State *L);
180  int intf_get_all_vars(lua_State *L);
181  int impl_theme_item(lua_State *L, std::string name);
182  int impl_theme_items_get(lua_State *L);
183  int impl_theme_items_set(lua_State *L);
184  int impl_theme_items_dir(lua_State *L);
185  int cfun_builtin_effect(lua_State *L);
186  int cfun_wml_action(lua_State *L);
187  int intf_fire_event(lua_State *L, const bool by_id);
188  int intf_fire_wml_menu_item(lua_State *L);
189  int intf_teleport(lua_State *L);
190  int intf_log(lua_State *L);
191  int intf_toggle_fog(lua_State *L, const bool clear);
192  int intf_get_fog_or_shroud(lua_State *L, bool fog);
193  int intf_log_replay(lua_State* L);
194  int intf_zoom(lua_State* L);
195 
196  //private helpers
197  std::string synced_state();
198  void lua_chat(const std::string& caption, const std::string& msg);
199  std::vector<int> get_sides_vector(const vconfig& cfg);
200 
201 public:
202  game_board & board();
203  std::vector<team> & teams();
204  const gamemap & map() const;
205  game_display * get_display() const { return game_display_; }
206  /**
207  A value != 0 means that the shouldn't remove any units from the map, usually because
208  we are currently operating on a unit& and removing it might cause memory corruptions
209  note that we don't check for the dtor of lua owned units because we assume that
210  we operate on such a unit that the lua function that invoked the operation on that unit
211  (like wesnoth.units.add_modification, wesnoth.units.matches ..) have a local copy of that
212  lua_unit* userdata in its stack that prevents it from being collected.
213  */
216 
217  void set_game_display(game_display * gd);
218 
219  virtual std::string my_name() override { return "Game Lua Kernel"; }
220 
221  std::string apply_effect(const std::string& name, unit& u, const config& cfg, bool need_apply);
222  void initialize(const config& level);
223  void save_game(config & level);
224  void load_game(const config& level);
226  void custom_command(const std::string&, const config&);
227  void push_builtin_effect();
228  void set_wml_action(const std::string&, game_events::wml_action::handler);
229  void set_wml_condition(const std::string&, bool(*)(const vconfig&));
230  bool run_wml_action(const std::string&, const vconfig&,
232  bool run_filter(char const *name, const unit& u);
233  bool run_filter(char const *name, const map_location& l);
234  bool run_filter(char const *name, const team& t);
235  bool run_filter(char const *name, int nArgs);
236  bool run_wml_conditional(const std::string&, const vconfig&);
237  /**
238  * Store a WML event in the Lua registry, as a function.
239  * Uses a default function that interprets ActionWML.
240  * @return A unique index into the EVENT_TABLE within the Lua registry
241  */
242  int save_wml_event();
243  /**
244  * Store a WML event in the Lua registry, as a function.
245  * Compiles the function from the given code.
246  * @param name The event name, used to generate a chunk name for the compiled function
247  * @param id The event id, used to generate a chunk name for the compiled function
248  * @param code The actual code of the function
249  * @return A unique index into the EVENT_TABLE within the Lua registry
250  */
251  int save_wml_event(const std::string& name, const std::string& id, const std::string& code);
252  /**
253  * Store a WML event in the Lua registry, as a function.
254  * Uses the function at the specified Lua stack index.
255  * @param idx The Lua stack index of the function to store
256  * @return A unique index into the EVENT_TABLE within the Lua registry
257  */
258  int save_wml_event(int idx);
259  /**
260  * Clear a WML event store in the Lua registry.
261  * @param ref The unique index into the EVENT_TABLE within the Lua registry
262  */
263  void clear_wml_event(int ref);
264  /**
265  * Run a WML stored in the Lua registry.
266  * @param ref The unique index into the EVENT_TABLE within the Lua registry
267  * @param args Arguments to pass to the event function, as a config
268  * @param ev The event data for the event being fired
269  * @param out If non-null, receives the result of the called function (provided it is a boolean value)
270  * @return Whether the function was successfully called; could be false if @a ref was invalid or if the function raised an error
271  */
272  bool run_wml_event(int ref, const vconfig& args, const game_events::queued_event& ev, bool* out = nullptr);
273 
274  virtual void log_error(char const* msg, char const* context = "Lua error") override;
275 
276  ai::lua_ai_context* create_lua_ai_context(char const *code, ai::engine_lua *engine);
278 
279  void mouse_over_hex_callback(const map_location& loc);
280  bool mouse_button_callback(const map_location& loc, const std::string &button, const std::string &event);
281  void select_hex_callback(const map_location& loc);
283 };
Define actions for the game's events mechanism.
double t
Definition: astarsearch.cpp:63
Proxy class for calling AI action handlers defined in Lua.
Definition: core.hpp:71
Proxy table for the AI context.
Definition: core.hpp:34
A config object defines a single node in a WML file, with access to child nodes.
Definition: config.hpp:172
Game board class.
Definition: game_board.hpp:47
A class grating read only view to a vector of config objects, viewed as one config with all children ...
void(* handler)(const queued_event &, const vconfig &)
Definition: action_wml.hpp:44
int intf_get_mouseover_tile(lua_State *L)
Returns the currently overed tile.
void custom_command(const std::string &, const config &)
int intf_put_unit(lua_State *L)
Places a unit on the map.
int intf_get_label(lua_State *L)
int intf_cancel_action(lua_State *)
int intf_set_floating_label(lua_State *L, bool spawn)
Arg 1: text - string Arg 2: options table.
int intf_replace_schedule(lua_State *l)
Replacing the current time of day schedule.
int intf_select_unit(lua_State *L)
Selects and highlights the given location on the map.
int intf_deselect_hex(lua_State *L)
Deselects any highlighted hex on the map.
std::stack< game_events::queued_event const * > queued_events_
int intf_get_all_vars(lua_State *L)
Gets all the WML variables currently set.
int intf_remove_tile_overlay(lua_State *L)
Removes an overlay from a tile.
int intf_screen_fade(lua_State *L)
int intf_erase_unit(lua_State *L)
Erases a unit from the map.
int intf_get_fog_or_shroud(lua_State *L, bool fog)
int intf_override_shroud(lua_State *L)
Overrides the shroud entirely.
int intf_get_variable(lua_State *L)
Gets a WML variable.
int intf_scroll(lua_State *L)
game_lua_kernel(game_state &, play_controller &, reports &)
int intf_set_sub_achievement(lua_State *L)
Marks a single sub-achievement as completed.
int intf_lock_view(lua_State *L)
Sets whether gamemap scrolling is disabled for the user.
void put_unit_helper(const map_location &loc)
int intf_toggle_shroud(lua_State *L, bool place_shroud)
Toggle shroud on some locations Arg 1: Side number Arg 2: List of locations on which to place/remove ...
int intf_match_side(lua_State *L)
Matches a side against the given filter.
int intf_get_selected_tile(lua_State *L)
Returns the currently selected tile.
int cfun_wml_action(lua_State *L)
Executes its upvalue as a wml action.
virtual void log_error(char const *msg, char const *context="Lua error") override
Error reporting mechanisms, used by virtual methods protected_call and load_string.
int cfun_builtin_effect(lua_State *L)
Applies its upvalue as an effect Arg 1: The unit to apply to Arg 3: The [effect] tag contents Arg 3: ...
ai::lua_ai_context * create_lua_ai_context(char const *code, ai::engine_lua *engine)
int intf_has_achievement(lua_State *L)
Returns whether an achievement has been completed.
int intf_gamestate_inspector(lua_State *)
int intf_float_label(lua_State *L)
Floats some text on the map.
tod_manager & tod_man()
int intf_find_reach(lua_State *L)
Finds all the locations reachable by a unit.
bool run_event(const game_events::queued_event &)
Executes the game_events.on_event function.
int intf_end_turn(lua_State *)
int save_wml_event()
Store a WML event in the Lua registry, as a function.
int impl_scenario_dir(lua_State *L)
Get a list of scenario data (__dir metamethod).
int intf_set_achievement(lua_State *L)
Sets an achievement as being completed.
int intf_get_units(lua_State *)
Gets all the units matching a given filter.
int intf_color_adjust(lua_State *L)
int intf_redraw(lua_State *L)
int intf_set_village_owner(lua_State *L)
Sets the owner of a village.
int impl_current_dir(lua_State *L)
Gets a list of date about current point of game (__dir metamethod).
static config preload_config
int intf_find_cost_map(lua_State *L)
Is called with one or more units and builds a cost map.
int intf_get_time_area(lua_State *)
int intf_highlight_hex(lua_State *L)
Highlights the given location on the map.
bool run_wml_event(int ref, const vconfig &args, const game_events::queued_event &ev, bool *out=nullptr)
Run a WML stored in the Lua registry.
int intf_scroll_to_tile(lua_State *L)
Scrolls to given tile.
int intf_get_side(lua_State *L)
int intf_remove_event(lua_State *L)
int intf_is_enemy(lua_State *L)
Returns whether the first side is an enemy of the second one.
static void extract_preload_scripts(const game_config_view &game_config)
int impl_get_terrain_info(lua_State *L)
Gets details about a terrain.
virtual std::string my_name() override
User-visible name of the lua kernel that they are talking to.
int intf_remove_label(lua_State *L)
bool run_wml_action(const std::string &, const vconfig &, const game_events::queued_event &)
Runs a command from an event handler.
int intf_move_floating_label(lua_State *L)
int intf_match_unit(lua_State *L)
Matches a unit against the given filter.
int intf_add_time_area(lua_State *)
Adding new time_areas dynamically with Standard Location Filters.
void clear_wml_event(int ref)
Clear a WML event store in the Lua registry.
int intf_create_animator(lua_State *)
int impl_theme_items_dir(lua_State *L)
Get all available theme_items (__dir metamethod).
int intf_add_event_wml(lua_State *L)
Add a new event handler Arg: A full event specification as a WML config.
int impl_scenario_set(lua_State *L)
Sets some scenario data (__newindex metamethod).
int intf_message(lua_State *L)
Displays a message in the chat window and in the logs.
int intf_set_side_id(lua_State *L)
int intf_view_locked(lua_State *L)
Gets whether gamemap scrolling is disabled for the user.
int intf_get_displayed_unit(lua_State *)
Gets the unit displayed in the sidebar.
bool run_wml_conditional(const std::string &, const vconfig &)
Evaluates a WML conidition.
int intf_get_recall_units(lua_State *L)
Gets the numeric ids of all the units matching a given filter on the recall lists.
int intf_add_label(lua_State *L)
int intf_zoom(lua_State *L)
int intf_log_replay(lua_State *L)
const game_events::queued_event & get_event_info()
int intf_unit_ability(lua_State *L)
Returns true if the unit has the given ability enabled.
void push_builtin_effect()
Registers a function for use as an effect handler.
int impl_run_animation(lua_State *)
std::string apply_effect(const std::string &name, unit &u, const config &cfg, bool need_apply)
game_board & board()
int intf_fire_wml_menu_item(lua_State *L)
Fires a wml menu item.
int intf_clear_menu_item(lua_State *L)
void mouse_over_hex_callback(const map_location &loc)
int impl_theme_items_get(lua_State *L)
Creates a field of the theme_items table and returns it (__index metamethod).
int intf_find_vacant_tile(lua_State *L)
Finds a vacant tile.
play_controller & play_controller_
int impl_schedule_dir(lua_State *L)
const gamemap & map() const
int map_locked_
A value != 0 means that the shouldn't remove any units from the map, usually because we are currently...
static std::vector< config > preload_scripts
int intf_get_unit(lua_State *)
Gets the unit at the given location or with the given id.
int impl_current_get(lua_State *L)
Gets some data about current point of game (__index metamethod).
int impl_schedule_set(lua_State *L)
void select_hex_callback(const map_location &loc)
void set_wml_condition(const std::string &, bool(*)(const vconfig &))
Registers a function for use as a conditional handler.
game_state & game_state_
int impl_end_level_data_set(lua_State *)
std::string synced_state()
converts synced_context::get_synced_state() to a string.
int intf_find_path(lua_State *L)
Finds a path between two locations.
int intf_remove_floating_label(lua_State *L)
int intf_animate_unit(lua_State *)
void set_wml_action(const std::string &, game_events::wml_action::handler)
Registers a function for use as an action handler.
int intf_put_recall_unit(lua_State *L)
Puts a unit on a recall list.
int intf_teleport(lua_State *L)
Teeleports a unit to a location.
void luaW_push_schedule(lua_State *L, int area_index)
int intf_add_tile_overlay(lua_State *L)
Adds an overlay on a tile.
int intf_play_sound(lua_State *L)
Plays a sound, possibly repeated.
void lua_chat(const std::string &caption, const std::string &msg)
int intf_allow_end_turn(lua_State *)
Allow undo sets the flag saying whether the event has mutated the game to false.
int intf_get_village_owner(lua_State *L)
Gets the side of a village owner.
int intf_heal_unit(lua_State *L)
int intf_get_sides(lua_State *L)
Returns a proxy table array for all sides matching the given SSF.
int intf_has_sub_achievement(lua_State *L)
Returns whether an achievement has been completed.
int intf_create_side(lua_State *L)
void initialize(const config &level)
int intf_add_undo_actions(lua_State *L)
Add undo actions for the current active event Arg 1: Either a table of ActionWML or a function to cal...
void save_game(config &level)
Executes the game_events.on_save function and adds to cfg the returned tags.
int impl_scenario_get(lua_State *L)
Gets some scenario data (__index metamethod).
int intf_remove_time_area(lua_State *)
Removing new time_areas dynamically with Standard Location Filters.
int impl_schedule_len(lua_State *L)
int intf_get_locations(lua_State *L)
Gets all the locations matching a given filter.
int intf_add_event(lua_State *L)
Add a new event handler Arg 1: Table of options.
int intf_simulate_combat(lua_State *L)
Simulates a combat between two units.
int impl_get_terrain_list(lua_State *L)
Gets a list of known terrain codes.
std::vector< team > & teams()
int intf_progress_achievement(lua_State *L)
Progresses the provided achievement.
int intf_match_location(lua_State *L)
Matches a location against the given filter.
int intf_toggle_fog(lua_State *L, const bool clear)
Implements the lifting and resetting of fog via WML.
int intf_extract_unit(lua_State *L)
Extracts a unit from the map or a recall list and gives it to Lua.
int intf_log(lua_State *L)
Logs a message Arg 1: (optional) Logger; "wml" for WML errors or deprecations Arg 2: Message Arg 3: W...
int intf_clear_messages(lua_State *)
Removes all messages from the chat window.
int intf_modify_ai_wml(lua_State *L)
int intf_allow_undo(lua_State *)
Allow undo sets the flag saying whether the event has mutated the game to false.
int impl_schedule_get(lua_State *L)
int intf_set_variable(lua_State *L)
Sets a WML variable.
int impl_theme_items_set(lua_State *L)
Sets a field of the theme_items table (__newindex metamethod).
void set_game_display(game_display *gd)
int intf_set_menu_item(lua_State *L)
game_display * get_display() const
ai::lua_ai_action_handler * create_lua_ai_action_handler(char const *code, ai::lua_ai_context &context)
int impl_theme_item(lua_State *L, std::string name)
Executes its upvalue as a theme item generator.
bool mouse_button_callback(const map_location &loc, const std::string &button, const std::string &event)
int intf_get_achievement(lua_State *L)
Returns information on a single achievement, or no data if the achievement is not found.
std::vector< int > get_sides_vector(const vconfig &cfg)
Gets a vector of sides from side= attribute in a given config node.
int intf_fire_event(lua_State *L, const bool by_id)
Fires an event.
int intf_delay(lua_State *L)
Delays engine for a while.
int intf_add_event_simple(lua_State *L)
Add a new event handler Arg 1: Event to handle, as a string or list of strings; or menu item ID if th...
bool run_filter(char const *name, const unit &u)
Runs a script from a unit filter.
int intf_find_vision_range(lua_State *L)
Finds all the locations for which a given unit would remove the fog (if there was fog on the map).
int intf_skip_messages(lua_State *L)
Set whether to skip messages Arg 1 (optional) - boolean.
game_display * game_display_
int cfun_undoable_event(lua_State *L)
Upvalue 1: The event function Upvalue 2: The undo function Arg 1: The event content.
void load_game(const config &level)
Executes the game_events.on_load function and passes to it all the scenario tags not yet handled.
int intf_get_time_of_day(lua_State *L)
Gets time of day information.
game_data & gamedata()
int intf_get_color_adjust(lua_State *L)
int intf_is_skipping_messages(lua_State *L)
Return true if a replay is in progress but the player has chosen to skip it.
Encapsulates the map of the game.
Definition: map.hpp:172
This class stores all the data for a single 'side' (in game nomenclature).
Definition: team.hpp:75
Container associating units to locations.
Definition: map.hpp:98
This class represents a single unit of a specific type.
Definition: unit.hpp:133
A variable-expanding proxy for the config class.
Definition: variable.hpp:45
int(* lua_CFunction)(lua_State *L)
A small explanation about what's going on here: Each action has access to two game_info objects First...
Definition: actions.cpp:59
void clear()
Clear the current render target.
Definition: draw.cpp:40
Game configuration data as global variables.
Definition: build_info.cpp:61
Unit and team statistics.
static void msg(const char *act, debug_info &i, const char *to="", const char *result="")
Definition: debugger.cpp:109
game_lua_kernel & ref
Encapsulates the map of the game.
Definition: location.hpp:45