The Battle for Wesnoth  1.19.13+dev
command_executor.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2003 - 2025
3  by David White <dave@whitevine.net>
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 
17 #include "hotkey/hotkey_item.hpp"
18 
19 #include "gui/gui.hpp"
22 #include "gui/dialogs/message.hpp"
25 #include "gui/widgets/retval.hpp"
26 #include "filesystem.hpp"
27 #include "gettext.hpp"
28 #include "log.hpp"
30 #include "display.hpp"
31 #include "quit_confirmation.hpp"
32 #include "sdl/surface.hpp"
33 #include "../resources.hpp"
34 #include "../playmp_controller.hpp"
35 #include "sdl/input.hpp" // get_mouse_state
36 #include "video.hpp" // toggle_fullscreen
37 
38 #include <ios>
39 #include <set>
40 
41 static lg::log_domain log_config("config");
42 static lg::log_domain log_hotkey("hotkey");
43 #define ERR_G LOG_STREAM(err, lg::general())
44 #define WRN_G LOG_STREAM(warn, lg::general())
45 #define LOG_G LOG_STREAM(info, lg::general())
46 #define DBG_G LOG_STREAM(debug, lg::general())
47 #define ERR_CF LOG_STREAM(err, log_config)
48 #define LOG_HK LOG_STREAM(info, log_hotkey)
49 
50 namespace {
51 
52 void make_screenshot(const std::string& name, bool map_screenshot)
53 {
54  surface screenshot = display::get_singleton()->screenshot(map_screenshot);
55  if(screenshot) {
56  std::string filename = filesystem::get_screenshot_dir() + "/" + name + "_";
58  gui2::dialogs::screenshot_notification::display(filename, screenshot);
59  }
60 }
61 }
62 namespace hotkey {
63 
64 static void event_queue(const SDL_Event& event, command_executor* executor);
65 
66 bool command_executor::do_execute_command(const hotkey::ui_command& cmd, bool press, bool release)
67 {
68  // hotkey release handling
69  if (release) {
70  switch(cmd.hotkey_command) {
71  // release a scroll key, un-apply scrolling in the given direction
72  case HOTKEY_SCROLL_UP:
73  scroll_up(false);
74  break;
75  case HOTKEY_SCROLL_DOWN:
76  scroll_down(false);
77  break;
78  case HOTKEY_SCROLL_LEFT:
79  scroll_left(false);
80  break;
82  scroll_right(false);
83  break;
84  default:
85  return false; // nothing else handles a hotkey release
86  }
87 
88  return true;
89  }
90 
91  // handling of hotkeys which activate even on hold events
92  switch(cmd.hotkey_command) {
95  return true;
96  case HOTKEY_SCROLL_UP:
97  scroll_up(true);
98  return true;
99  case HOTKEY_SCROLL_DOWN:
100  scroll_down(true);
101  return true;
102  case HOTKEY_SCROLL_LEFT:
103  scroll_left(true);
104  return true;
105  case HOTKEY_SCROLL_RIGHT:
106  scroll_right(true);
107  return true;
108  default:
109  break;
110  }
111 
112  if(!press) {
113  return false; // nothing else handles hotkey hold events
114  }
115 
116  // hotkey press handling
117  switch(cmd.hotkey_command) {
118  case HOTKEY_CYCLE_UNITS:
119  cycle_units();
120  break;
123  break;
124  case HOTKEY_ENDTURN:
125  end_turn();
126  break;
129  break;
131  end_unit_turn();
132  break;
133  case HOTKEY_LEADER:
134  goto_leader();
135  break;
136  case HOTKEY_UNDO:
137  undo();
138  break;
139  case HOTKEY_REDO:
140  redo();
141  break;
144  break;
147  break;
148  case HOTKEY_RENAME_UNIT:
149  rename_unit();
150  break;
151  case HOTKEY_SAVE_GAME:
152  save_game();
153  break;
154  case HOTKEY_SAVE_REPLAY:
155  save_replay();
156  break;
157  case HOTKEY_SAVE_MAP:
158  save_map();
159  break;
160  case HOTKEY_LOAD_GAME:
161  load_game();
162  break;
164  toggle_ellipses();
165  break;
166  case HOTKEY_TOGGLE_GRID:
167  toggle_grid();
168  break;
169  case HOTKEY_STATUS_TABLE:
170  status_table();
171  break;
172  case HOTKEY_RECALL:
173  recall();
174  break;
176  label_settings();
177  break;
178  case HOTKEY_RECRUIT:
179  recruit();
180  break;
181  case HOTKEY_SPEAK:
182  speak();
183  break;
184  case HOTKEY_SPEAK_ALLY:
185  whisper();
186  break;
187  case HOTKEY_SPEAK_ALL:
188  shout();
189  break;
190  case HOTKEY_CREATE_UNIT:
191  create_unit();
192  break;
193  case HOTKEY_CHANGE_SIDE:
194  change_side();
195  break;
196  case HOTKEY_KILL_UNIT:
197  kill_unit();
198  break;
200  select_teleport();
201  break;
202  case HOTKEY_PREFERENCES:
203  preferences();
204  break;
205  case HOTKEY_OBJECTIVES:
206  objectives();
207  break;
208  case HOTKEY_UNIT_LIST:
209  unit_list();
210  break;
211  case HOTKEY_STATISTICS:
212  show_statistics();
213  break;
214  case HOTKEY_STOP_NETWORK:
215  stop_network();
216  break;
218  start_network();
219  break;
221  label_terrain(true);
222  break;
224  label_terrain(false);
225  break;
226  case HOTKEY_CLEAR_LABELS:
227  clear_labels();
228  break;
230  show_enemy_moves(false);
231  break;
233  show_enemy_moves(true);
234  break;
235  case HOTKEY_DELAY_SHROUD:
237  break;
240  break;
242  continue_move();
243  break;
244  case HOTKEY_SEARCH:
245  search();
246  break;
247  case HOTKEY_HELP:
248  show_help();
249  break;
251  // although HOTKEY_HELP uses a virtual call to allow context-specific help, this one is already a specific topic
252  help::show_help("saveload");
253  break;
254  case HOTKEY_CHAT_LOG:
255  show_chat_log();
256  break;
257  case HOTKEY_USER_CMD:
258  user_command();
259  break;
260  case HOTKEY_CUSTOM_CMD:
261  custom_command();
262  break;
263  case HOTKEY_AI_FORMULA:
264  ai_formula();
265  break;
266  case HOTKEY_CLEAR_MSG:
267  clear_messages();
268  break;
269  case HOTKEY_LANGUAGE:
270  change_language();
271  break;
272  case HOTKEY_REPLAY_PLAY:
273  play_replay();
274  break;
275  case HOTKEY_REPLAY_RESET:
276  reset_replay();
277  break;
278  case HOTKEY_REPLAY_STOP:
279  stop_replay();
280  break;
283  break;
286  break;
289  break;
292  break;
295  break;
298  break;
301  break;
302  case HOTKEY_REPLAY_EXIT:
303  replay_exit();
304  break;
305  case HOTKEY_WB_TOGGLE:
307  break;
310  break;
313  break;
316  break;
319  break;
322  break;
325  break;
326  case HOTKEY_SELECT_HEX:
327  select_hex();
328  break;
329  case HOTKEY_DESELECT_HEX:
330  deselect_hex();
331  break;
332  case HOTKEY_MOVE_ACTION:
333  move_action();
334  break;
337  break;
338  case HOTKEY_TOUCH_HEX:
339  touch_hex();
340  break;
341  case HOTKEY_ACCELERATED:
343  break;
344  case LUA_CONSOLE:
345  lua_console();
346  break;
347  case HOTKEY_ZOOM_IN:
348  zoom_in();
349  break;
350  case HOTKEY_ZOOM_OUT:
351  zoom_out();
352  break;
353  case HOTKEY_ZOOM_DEFAULT:
354  zoom_default();
355  break;
357  map_screenshot();
358  break;
361  break;
362  case HOTKEY_QUIT_GAME:
363  gui2::switch_theme(prefs::get().gui2_theme());
365  break;
366  case HOTKEY_SURRENDER:
367  surrender_game();
368  break;
370  prefs::get().set_minimap_draw_terrain(!prefs::get().minimap_draw_terrain());
372  break;
374  prefs::get().set_minimap_terrain_coding(!prefs::get().minimap_terrain_coding());
376  break;
378  prefs::get().set_minimap_movement_coding(!prefs::get().minimap_movement_coding());
380  break;
382  prefs::get().set_minimap_draw_units(!prefs::get().minimap_draw_units());
384  break;
386  prefs::get().set_minimap_draw_villages(!prefs::get().minimap_draw_villages());
388  break;
389  case HOTKEY_ACHIEVEMENTS:
390  {
392  ach.show();
393  }
394  break;
395  default:
396  return false;
397  }
398  return true;
399 }
400 
402  if(gui2::show_message(_("Surrender"), _("Do you really want to surrender the game?"), gui2::dialogs::message::yes_no_buttons) != gui2::retval::CANCEL) {
404  if(pmc && !pmc->is_linger_mode() && !pmc->is_observer()) {
406  }
407  }
408 }
409 
410 void command_executor::show_menu(const std::vector<config>& items_arg, int xloc, int yloc, bool /*context_menu*/)
411 {
412  if(items_arg.empty()) {
413  return;
414  }
415 
416  // FIXME: take the argument by value
417  std::vector<config> items = items_arg;
418  for(std::size_t i = 0; i < items.size(); ++i) {
419  populate_menu_item_info(items[i], i);
420  }
421 
422  const auto do_command = [&](int selected_item) {
423  std::string id = items[selected_item]["id"].str();
424  do_execute_command(hotkey::ui_command(id, selected_item));
426  };
427 
428  int res = -1;
429  point selection_pos;
430  {
431  SDL_Rect pos {xloc, yloc, 1, 1};
432  gui2::dialogs::drop_down_menu mmenu(pos, items, -1, true, keep_menu_open());
433 
434  // Transitional API. Remove once the game UI is using GUI2.
435  // Callback will only fire if keep_menu_open is false
436  mmenu.set_legacy_menu_mode(true);
437  mmenu.set_legacy_toggle_callback(do_command);
438 
439  if(mmenu.show()) {
440  res = mmenu.selected_item();
441  if(res >= 0) {
442  // Get selection coordinates for a potential submenu below
443  selection_pos = mmenu.selected_item_pos();
444  // Compensate for borders
445  selection_pos.x--;
446  selection_pos.y--;
447  }
448  }
449  } // This will kill the dialog.
450 
451  if(res < 0 || std::size_t(res) >= items.size()) {
452  return;
453  }
454 
455  std::string id = items[res]["id"];
456  if(const theme::menu* submenu = display::get_singleton()->get_theme().get_menu_item(id)) {
457  show_menu(submenu->items(), selection_pos.x, selection_pos.y, submenu->is_context());
458  } else {
459  do_command(res);
460  }
461 }
462 
463 void command_executor::execute_action(const std::vector<std::string>& items_arg)
464 {
465  for(const std::string& item : items_arg) {
466  auto cmd = hotkey::ui_command(item);
467  if(can_execute_command(cmd)) {
468  do_execute_command(cmd);
470  }
471  }
472 }
473 
475 {
476  const std::string& command = item["id"];
477 
478  // FIXME: better integrate this with GUI2
479  const std::string default_image = "icons/action/" + command + "_25.png";
480  const std::string pressed_image = "icons/action/" + command + "_25-pressed.png";
481 
482  auto cmd = hotkey::ui_command(command, index);
484 
485  // An image set, if present, takes precedence over toggle buttons to represent
486  // an item's state. See the editor's terrain category dropdown for an example.
487  if(filesystem::file_exists(game_config::path + "/images/" + default_image)) {
488  switch(state) {
489  case action_state::on:
491  item["icon"] = pressed_image + "~CROP(3,3,18,18)";
492  return;
493  default:
494  item["icon"] = default_image + "~CROP(3,3,18,18)";
495  return;
496  }
497  }
498 
499  switch(state) {
500  case action_state::on:
501  item["checkbox"] = true;
502  break;
503  case action_state::off:
504  item["checkbox"] = false;
505  break;
507  item["radio"] = true;
508  break;
510  item["radio"] = false;
511  break;
513  // Do nothing
514  break;
515  }
516 }
517 
519 {
520  const std::string& item_id = item["id"];
521  const auto& hk = hotkey::get_hotkey_command(item_id);
523 
524  // Submenu
525  if(const theme::menu* menu = theme.get_menu_item(item_id)) {
526  item["icon"] = "icons/arrows/short_arrow_right_25.png~CROP(3,3,18,18)"; // TODO: should not be hardcoded
527  item["label"] = menu->title();
528  return;
529  }
530 
531  // Populate icons and enable toggle buttons
533 
534  if(hk.command != hotkey::HOTKEY_NULL) {
535  std::string desc = hk.description;
536 
537  // TODO: why does this get special handling?
538  if(hk.command == HOTKEY_ENDTURN) {
539  if(const theme::action* b = theme.get_action_item("button-endturn")) {
540  desc = b->title();
541  }
542  }
543 
544  item["label"] = desc;
545  item["details"] = hotkey::get_names(item_id);
546  }
547 }
548 
549 void mbutton_event(const SDL_Event& event, command_executor* executor)
550 {
551  event_queue(event, executor);
552 
553  /* Run mouse events immediately.
554 
555  This is necessary because the sidebar doesn't allow set_button_state() to be called after a
556  button has received the mouse press event but before it has received the mouse release event.
557  When https://github.com/wesnoth/wesnoth/pull/2872 delayed the processing of input events,
558  set_button_state() ended up being called at such a time. However, if we run the event handlers
559  now, the button (if any) hasn't received the press event yet and we can call set_button_state()
560  safely.
561 
562  See https://github.com/wesnoth/wesnoth/issues/2884 */
563 
564  run_events(executor);
565 }
566 
567 void jbutton_event(const SDL_Event& event, command_executor* executor)
568 {
569  event_queue(event, executor);
570 }
571 
572 void jhat_event(const SDL_Event& event, command_executor* executor)
573 {
574  event_queue(event, executor);
575 }
576 
577 void key_event(const SDL_Event& event, command_executor* executor)
578 {
579  if (!executor) return;
580  event_queue(event,executor);
581 }
582 
583 void keyup_event(const SDL_Event&, command_executor* executor)
584 {
585  if(!executor) return;
586  executor->handle_keyup();
587 }
588 
590 {
591  if(!executor) return;
592  bool commands_ran = executor->run_queued_commands();
593  if(commands_ran) {
594  executor->set_button_state();
595  }
596 }
597 
598 static void event_queue(const SDL_Event& event, command_executor* executor)
599 {
600  if (!executor) return;
601  executor->queue_command(event);
602  executor->set_button_state();
603 }
604 
605 void command_executor::queue_command(const SDL_Event& event, int index)
606 {
607  LOG_HK << "event 0x" << std::hex << event.type << std::dec;
608  if(event.type == SDL_TEXTINPUT) {
609  LOG_HK << "SDL_TEXTINPUT \"" << event.text.text << "\"";
610  }
611 
612  const hotkey_ptr hk = get_hotkey(event);
613  if(!hk->active() || hk->is_disabled()) {
614  return;
615  }
616 
617  const hotkey_command& command = hotkey::get_hotkey_command(hk->get_command());
618  bool keypress = (event.type == SDL_KEYDOWN || event.type == SDL_TEXTINPUT) &&
620  bool press = keypress ||
621  (event.type == SDL_JOYBUTTONDOWN || event.type == SDL_MOUSEBUTTONDOWN || event.type == SDL_FINGERDOWN);
622  bool release = event.type == SDL_KEYUP;
623  if(press) {
624  LOG_HK << "sending press event (keypress = " <<
625  std::boolalpha << keypress << std::noboolalpha << ")";
626  }
627  if(keypress) {
628  press_event_sent_ = true;
629  }
630 
631  command_queue_.emplace_back(command, index, press, release);
632 }
633 
635 {
636  auto ui_cmd = hotkey::ui_command(*command.command, command.index);
637  if (!can_execute_command(ui_cmd)
638  || do_execute_command(ui_cmd, command.press, command.release)) {
639  return;
640  }
641 
642  if (!command.press) {
643  return; // none of the commands here respond to a key release
644  }
645 
646  switch(command.command->command) {
647  case HOTKEY_FULLSCREEN:
649  break;
650  case HOTKEY_SCREENSHOT:
651  make_screenshot(_("Screenshot"), false);
652  break;
653  case HOTKEY_ANIMATE_MAP:
654  prefs::get().set_animate_map(!prefs::get().animate_map());
655  break;
656  case HOTKEY_MOUSE_SCROLL:
657  prefs::get().set_mouse_scrolling(!prefs::get().mouse_scrolling());
658  break;
659  case HOTKEY_MUTE:
660  {
661  // look if both is not playing
662  static struct before_muted_s
663  {
664  bool playing_sound,playing_music;
665  before_muted_s() : playing_sound(false),playing_music(false){}
666  } before_muted;
667  if (prefs::get().music_on() || prefs::get().sound())
668  {
669  // then remember settings and mute both
670  before_muted.playing_sound = prefs::get().sound();
671  before_muted.playing_music = prefs::get().music_on();
672  prefs::get().set_sound(false);
673  prefs::get().set_music(false);
674  }
675  else
676  {
677  // then set settings before mute
678  prefs::get().set_sound(before_muted.playing_sound);
679  prefs::get().set_music(before_muted.playing_music);
680  }
681  }
682  break;
683  default:
684  DBG_G << "command_executor: unknown command number " << command.command->command << ", ignoring.";
685  break;
686  }
687 }
688 
690 {
691  display& disp = get_display();
692  for (const theme::menu& menu : disp.get_theme().menus()) {
693 
694  std::shared_ptr<gui::button> button = disp.find_menu_button(menu.get_id());
695  if (!button) continue;
696  bool enabled = false;
697  for (const auto& command : menu.items()) {
698 
699  ui_command command_obj = ui_command(command["id"].str());
700  bool can_execute = can_execute_command(command_obj);
701  if (can_execute) {
702  enabled = true;
703  break;
704  }
705  }
706  button->enable(enabled);
707  }
708 
709  for (const theme::action& action : disp.get_theme().actions()) {
710 
711  std::shared_ptr<gui::button> button = disp.find_action_button(action.get_id());
712  if (!button) continue;
713  bool enabled = false;
714  int i = 0;
715  for (const std::string& command : action.items()) {
716 
717  ui_command command_obj = ui_command(command);
718  std::string tooltip = action.tooltip(i);
719  if (filesystem::file_exists(game_config::path + "/images/icons/action/" + command + "_25.png" ))
720  button->set_overlay("icons/action/" + command);
721  if (!tooltip.empty())
722  button->set_tooltip_string(tooltip);
723 
724  bool can_execute = can_execute_command(command_obj);
725  i++;
726  if (!can_execute) continue;
727  enabled = true;
728 
729  action_state state = get_action_state(command_obj);
730  switch (state) {
732  case action_state::on:
733  button->set_check(true);
734  break;
735  case action_state::off:
737  button->set_check(false);
738  break;
740  break;
741  default:
742  break;
743  }
744 
745  break;
746  }
747  button->enable(enabled);
748  }
749 }
750 
751 // Removes duplicate commands caused by both SDL_KEYDOWN and SDL_TEXTINPUT triggering hotkeys.
752 // See https://github.com/wesnoth/wesnoth/issues/1736
753 std::vector<command_executor::queued_command> command_executor::filter_command_queue()
754 {
755  std::vector<queued_command> filtered_commands;
756 
757  /** A command plus "key released" flag. Otherwise, we will filter out key releases that are preceded by a keypress. */
758  using command_with_keyrelease = std::pair<const hotkey_command*, bool>;
759  std::set<command_with_keyrelease> seen_commands;
760 
761  for(const queued_command& cmd : command_queue_) {
762  command_with_keyrelease command_key(cmd.command, cmd.release);
763  if(seen_commands.find(command_key) == seen_commands.end()) {
764  seen_commands.insert(command_key);
765  filtered_commands.push_back(cmd);
766  }
767  }
768 
769  command_queue_.clear();
770 
771  return filtered_commands;
772 }
773 
775 {
776  std::vector<queued_command> commands = filter_command_queue();
777  for(const queued_command& cmd : commands) {
779  }
780 
781  return !commands.empty();
782 }
783 
785 {
787 }
788 
790 {
792 }
793 
795 {
796  if (get_display().in_game()) {
798  } else {
800  }
801 }
802 
804 {
806 }
807 
809 {
810  if(!get_display().view_locked()) {
811  get_display().set_zoom(true);
812  }
813 }
814 
816 {
817  if(!get_display().view_locked()) {
818  get_display().set_zoom(false);
819  }
820 }
821 
823 {
824  if(!get_display().view_locked()) {
826  }
827 }
828 
830 {
831  make_screenshot(_("Map-Screenshot"), true);
832 }
833 }
A config object defines a single node in a WML file, with access to child nodes.
Definition: config.hpp:158
Sort-of-Singleton that many classes, both GUI and non-GUI, use to access the game data.
Definition: display.hpp:88
void recalculate_minimap()
Schedule the minimap for recalculation.
Definition: display.cpp:1455
std::shared_ptr< gui::button > find_action_button(const std::string &id)
Retrieves a pointer to a theme UI button.
Definition: display.cpp:759
std::shared_ptr< gui::button > find_menu_button(const std::string &id)
Definition: display.cpp:769
bool set_zoom(bool increase)
Zooms the display in (true) or out (false).
Definition: display.cpp:1682
surface screenshot(bool map_screenshot=false)
Capture a (map-)screenshot into a surface.
Definition: display.cpp:714
theme & get_theme()
Definition: display.hpp:381
void toggle_default_zoom()
Sets the zoom amount to the default.
Definition: display.cpp:1750
static display * get_singleton()
Returns the display object if a display object exists.
Definition: display.hpp:102
std::size_t viewing_team_index() const
The viewing team is the team currently viewing the game.
Definition: display.hpp:117
Used by the menu_button widget.
void set_legacy_toggle_callback(const Func &f)
void set_legacy_menu_mode(bool value)
static void display(lua_kernel_base *lk)
Display a new console, using given video and lua kernel.
@ yes_no_buttons
Shows a yes and no button.
Definition: message.hpp:81
bool show(const unsigned auto_close_time=0)
Shows the window.
virtual display & get_display()=0
virtual void scroll_right(bool)
virtual void replay_skip_animation()
virtual void scroll_up(bool)
virtual void scroll_left(bool)
virtual void whiteboard_execute_all_actions()
virtual bool do_execute_command(const hotkey::ui_command &command, bool press=true, bool release=false)
virtual void whiteboard_execute_action()
virtual void show_enemy_moves(bool)
std::vector< queued_command > command_queue_
virtual void toggle_shroud_updates()
virtual void whiteboard_bump_down_action()
void execute_command_wrap(const queued_command &command)
void execute_action(const std::vector< std::string > &items_arg)
virtual action_state get_action_state(const hotkey::ui_command &) const
virtual void whiteboard_delete_action()
virtual bool keep_menu_open() const
If true, the menu will remain open after an item has been selected.
virtual void replay_show_everything()
virtual void toggle_accelerated_speed()
virtual void whiteboard_suppose_dead()
void populate_menu_item_info(config &item, int index) const
virtual void scroll_down(bool)
virtual void show_menu(const std::vector< config > &items_arg, int xloc, int yloc, bool context_menu)
virtual void label_terrain(bool)
virtual void whiteboard_bump_up_action()
virtual void unit_hold_position()
virtual void terrain_description()
virtual void recalculate_minimap()
virtual bool can_execute_command(const hotkey::ui_command &command) const =0
std::vector< queued_command > filter_command_queue()
void queue_command(const SDL_Event &event, int index=-1)
void populate_menu_controls(config &item, int index) const
bool is_linger_mode() const
bool is_observer() const
void surrender(int side_number)
bool set_music(bool ison)
static prefs & get()
bool sound()
bool set_sound(bool ison)
bool music_on()
static void quit_to_desktop()
static void quit_to_title()
Definition: theme.hpp:44
const action * get_action_item(const std::string &key) const
Definition: theme.cpp:924
const menu * get_menu_item(const std::string &key) const
Definition: theme.cpp:915
const std::vector< action > & actions() const
Definition: theme.hpp:259
const std::vector< menu > & menus() const
Definition: theme.hpp:257
#define LOG_HK
static lg::log_domain log_hotkey("hotkey")
#define DBG_G
static lg::log_domain log_config("config")
map_display and display: classes which take care of displaying the map and game-data on the screen.
Declarations for File-IO.
std::size_t i
Definition: function.cpp:1032
static std::string _(const char *str)
Definition: gettext.hpp:97
std::string tooltip
Shown when hovering over an entry in the filter's drop-down list.
Definition: manager.cpp:203
Contains functions for cleanly handling SDL input.
Standard logging facilities (interface).
static bool file_exists(const bfs::path &fpath)
Definition: filesystem.cpp:341
std::string get_screenshot_dir()
std::string get_next_filename(const std::string &name, const std::string &extension)
Get the next free filename using "name + number (3 digits) + extension" maximum 1000 files then start...
Definition: filesystem.cpp:601
std::string path
Definition: filesystem.cpp:106
static bool sound()
static bool music_on()
void switch_theme(const std::string &theme_id)
Set and activate the given gui2 theme.
Definition: gui.cpp:153
void show_message(const std::string &title, const std::string &msg, const std::string &button_caption, const bool auto_close, const bool message_use_markup, const bool title_use_markup)
Shows a message to the user.
Definition: message.cpp:148
@ CANCEL
Dialog was closed with the CANCEL button.
Definition: retval.hpp:38
void show_help(const std::string &show_topic)
Open the help browser, show topic with id show_topic.
Definition: help.cpp:139
Keyboard shortcuts for game actions.
void jhat_event(const SDL_Event &event, command_executor *executor)
void key_event(const SDL_Event &event, command_executor *executor)
void mbutton_event(const SDL_Event &event, command_executor *executor)
static void event_queue(const SDL_Event &event, command_executor *executor)
std::string get_names(const std::string &id)
Returns a comma-separated string of hotkey names.
std::shared_ptr< class hotkey_base > hotkey_ptr
Definition: hotkey_item.hpp:27
const hotkey_ptr get_hotkey(const SDL_Event &event)
Iterate through the list of hotkeys and return a hotkey that matches the SDL_Event and the current ke...
void run_events(command_executor *executor)
void jbutton_event(const SDL_Event &event, command_executor *executor)
const hotkey_command & get_hotkey_command(std::string_view command)
Returns the hotkey_command with the given id.
void keyup_event(const SDL_Event &, command_executor *executor)
@ HOTKEY_MINIMAP_DRAW_VILLAGES
@ HOTKEY_FULLSCREEN
@ HOTKEY_OBJECTIVES
@ HOTKEY_ANIMATE_MAP
@ HOTKEY_SCREENSHOT
@ HOTKEY_TELEPORT_UNIT
@ HOTKEY_SPEAK_ALLY
@ HOTKEY_ACCELERATED
@ HOTKEY_MOUSE_SCROLL
@ HOTKEY_TERRAIN_DESCRIPTION
@ HOTKEY_END_UNIT_TURN
@ HOTKEY_LABEL_SETTINGS
@ HOTKEY_WB_EXECUTE_ALL_ACTIONS
@ HOTKEY_WB_SUPPOSE_DEAD
@ HOTKEY_HELP_ABOUT_SAVELOAD
@ HOTKEY_REPLAY_PLAY
@ HOTKEY_SCROLL_LEFT
@ HOTKEY_SAVE_GAME
@ HOTKEY_SPEAK_ALL
@ HOTKEY_SHOW_ENEMY_MOVES
@ HOTKEY_ACHIEVEMENTS
@ HOTKEY_DESELECT_HEX
@ HOTKEY_UNIT_DESCRIPTION
@ HOTKEY_UPDATE_SHROUD
@ HOTKEY_REPEAT_RECRUIT
@ HOTKEY_REPLAY_STOP
@ HOTKEY_KILL_UNIT
@ HOTKEY_SCROLL_RIGHT
@ HOTKEY_SAVE_REPLAY
@ HOTKEY_LABEL_TEAM_TERRAIN
@ HOTKEY_UNIT_HOLD_POSITION
@ HOTKEY_REPLAY_NEXT_TURN
@ HOTKEY_TOGGLE_GRID
@ HOTKEY_SURRENDER
@ HOTKEY_SELECT_AND_ACTION
@ HOTKEY_CLEAR_MSG
@ HOTKEY_REPLAY_SHOW_EVERYTHING
@ HOTKEY_REPLAY_SHOW_TEAM1
@ HOTKEY_MINIMAP_DRAW_TERRAIN
@ HOTKEY_LABEL_TERRAIN
@ HOTKEY_CUSTOM_CMD
@ HOTKEY_STOP_NETWORK
@ HOTKEY_MAP_SCREENSHOT
@ HOTKEY_CLEAR_LABELS
@ HOTKEY_CONTINUE_MOVE
@ HOTKEY_BEST_ENEMY_MOVES
@ HOTKEY_QUIT_TO_DESKTOP
@ HOTKEY_TOGGLE_ELLIPSES
@ HOTKEY_RENAME_UNIT
@ HOTKEY_MINIMAP_CODING_TERRAIN
@ HOTKEY_LOAD_GAME
@ HOTKEY_WB_EXECUTE_ACTION
@ HOTKEY_MINIMAP_DRAW_UNITS
@ HOTKEY_CHANGE_SIDE
@ HOTKEY_CYCLE_UNITS
@ HOTKEY_DELAY_SHROUD
@ HOTKEY_WB_BUMP_UP_ACTION
@ HOTKEY_CREATE_UNIT
@ HOTKEY_REPLAY_EXIT
@ HOTKEY_PREFERENCES
@ HOTKEY_STATUS_TABLE
@ HOTKEY_REPLAY_NEXT_SIDE
@ HOTKEY_MOVE_ACTION
@ HOTKEY_REPLAY_NEXT_MOVE
@ HOTKEY_REPLAY_RESET
@ HOTKEY_TOUCH_HEX
@ HOTKEY_START_NETWORK
@ HOTKEY_WB_TOGGLE
@ HOTKEY_STATISTICS
@ HOTKEY_UNIT_LIST
@ HOTKEY_SCROLL_DOWN
@ HOTKEY_REPLAY_SKIP_ANIMATION
@ HOTKEY_ZOOM_DEFAULT
@ HOTKEY_WB_BUMP_DOWN_ACTION
@ HOTKEY_SCROLL_UP
@ HOTKEY_SELECT_HEX
@ HOTKEY_QUIT_GAME
@ HOTKEY_AI_FORMULA
@ HOTKEY_REPLAY_SHOW_EACH
@ HOTKEY_CYCLE_BACK_UNITS
@ HOTKEY_WB_DELETE_ACTION
@ HOTKEY_MINIMAP_CODING_UNIT
play_controller * controller
Definition: resources.cpp:21
std::size_t index(std::string_view str, const std::size_t index)
Codepoint index corresponding to the nth character in a UTF-8 string.
Definition: unicode.cpp:70
void toggle_fullscreen()
Toggle fullscreen mode.
Definition: video.cpp:825
std::string filename
Filename.
Stores all information related to functions that can be bound to hotkeys.
HOTKEY_COMMAND command
The command associated with this hotkey.
Used as the main parameter for can_execute_command/do_execute_command These functions are used to exe...
hotkey::HOTKEY_COMMAND hotkey_command
The hotkey::HOTKEY_COMMAND associated with this action, HOTKEY_NULL for actions that don't allow hotk...
Holds a 2D point.
Definition: point.hpp:25
#define b