The Battle for Wesnoth  1.19.7+dev
command_executor.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2003 - 2024
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 
39 
40 #include <ios>
41 #include <set>
42 
43 static lg::log_domain log_config("config");
44 static lg::log_domain log_hotkey("hotkey");
45 #define ERR_G LOG_STREAM(err, lg::general())
46 #define WRN_G LOG_STREAM(warn, lg::general())
47 #define LOG_G LOG_STREAM(info, lg::general())
48 #define DBG_G LOG_STREAM(debug, lg::general())
49 #define ERR_CF LOG_STREAM(err, log_config)
50 #define LOG_HK LOG_STREAM(info, log_hotkey)
51 
52 namespace {
53 
54 void make_screenshot(const std::string& name, bool map_screenshot)
55 {
56  surface screenshot = display::get_singleton()->screenshot(map_screenshot);
57  if(screenshot) {
58  std::string filename = filesystem::get_screenshot_dir() + "/" + name + "_";
60  gui2::dialogs::screenshot_notification::display(filename, screenshot);
61  }
62 }
63 }
64 namespace hotkey {
65 
66 static void event_queue(const SDL_Event& event, command_executor* executor);
67 
68 bool command_executor::do_execute_command(const hotkey::ui_command& cmd, bool press, bool release)
69 {
70  // hotkey release handling
71  if (release) {
72  switch(cmd.hotkey_command) {
73  // release a scroll key, un-apply scrolling in the given direction
74  case HOTKEY_SCROLL_UP:
75  scroll_up(false);
76  break;
77  case HOTKEY_SCROLL_DOWN:
78  scroll_down(false);
79  break;
80  case HOTKEY_SCROLL_LEFT:
81  scroll_left(false);
82  break;
84  scroll_right(false);
85  break;
86  default:
87  return false; // nothing else handles a hotkey release
88  }
89 
90  return true;
91  }
92 
93  // handling of hotkeys which activate even on hold events
94  switch(cmd.hotkey_command) {
97  return true;
98  case HOTKEY_SCROLL_UP:
99  scroll_up(true);
100  return true;
101  case HOTKEY_SCROLL_DOWN:
102  scroll_down(true);
103  return true;
104  case HOTKEY_SCROLL_LEFT:
105  scroll_left(true);
106  return true;
107  case HOTKEY_SCROLL_RIGHT:
108  scroll_right(true);
109  return true;
110  default:
111  break;
112  }
113 
114  if(!press) {
115  return false; // nothing else handles hotkey hold events
116  }
117 
118  // hotkey press handling
119  switch(cmd.hotkey_command) {
120  case HOTKEY_CYCLE_UNITS:
121  cycle_units();
122  break;
125  break;
126  case HOTKEY_ENDTURN:
127  end_turn();
128  break;
131  break;
133  end_unit_turn();
134  break;
135  case HOTKEY_LEADER:
136  goto_leader();
137  break;
138  case HOTKEY_UNDO:
139  undo();
140  break;
141  case HOTKEY_REDO:
142  redo();
143  break;
146  break;
149  break;
150  case HOTKEY_RENAME_UNIT:
151  rename_unit();
152  break;
153  case HOTKEY_SAVE_GAME:
154  save_game();
155  break;
156  case HOTKEY_SAVE_REPLAY:
157  save_replay();
158  break;
159  case HOTKEY_SAVE_MAP:
160  save_map();
161  break;
162  case HOTKEY_LOAD_GAME:
163  load_game();
164  break;
166  toggle_ellipses();
167  break;
168  case HOTKEY_TOGGLE_GRID:
169  toggle_grid();
170  break;
171  case HOTKEY_STATUS_TABLE:
172  status_table();
173  break;
174  case HOTKEY_RECALL:
175  recall();
176  break;
178  label_settings();
179  break;
180  case HOTKEY_RECRUIT:
181  recruit();
182  break;
183  case HOTKEY_SPEAK:
184  speak();
185  break;
186  case HOTKEY_SPEAK_ALLY:
187  whisper();
188  break;
189  case HOTKEY_SPEAK_ALL:
190  shout();
191  break;
192  case HOTKEY_CREATE_UNIT:
193  create_unit();
194  break;
195  case HOTKEY_CHANGE_SIDE:
196  change_side();
197  break;
198  case HOTKEY_KILL_UNIT:
199  kill_unit();
200  break;
202  select_teleport();
203  break;
204  case HOTKEY_PREFERENCES:
205  preferences();
206  break;
207  case HOTKEY_OBJECTIVES:
208  objectives();
209  break;
210  case HOTKEY_UNIT_LIST:
211  unit_list();
212  break;
213  case HOTKEY_STATISTICS:
214  show_statistics();
215  break;
216  case HOTKEY_STOP_NETWORK:
217  stop_network();
218  break;
220  start_network();
221  break;
223  label_terrain(true);
224  break;
226  label_terrain(false);
227  break;
228  case HOTKEY_CLEAR_LABELS:
229  clear_labels();
230  break;
232  show_enemy_moves(false);
233  break;
235  show_enemy_moves(true);
236  break;
237  case HOTKEY_DELAY_SHROUD:
239  break;
242  break;
244  continue_move();
245  break;
246  case HOTKEY_SEARCH:
247  search();
248  break;
249  case HOTKEY_HELP:
250  show_help();
251  break;
253  // although HOTKEY_HELP uses a virtual call to allow context-specific help, this one is already a specific topic
254  help::show_help("saveload");
255  break;
256  case HOTKEY_CHAT_LOG:
257  show_chat_log();
258  break;
259  case HOTKEY_USER_CMD:
260  user_command();
261  break;
262  case HOTKEY_CUSTOM_CMD:
263  custom_command();
264  break;
265  case HOTKEY_AI_FORMULA:
266  ai_formula();
267  break;
268  case HOTKEY_CLEAR_MSG:
269  clear_messages();
270  break;
271  case HOTKEY_LANGUAGE:
272  change_language();
273  break;
274  case HOTKEY_REPLAY_PLAY:
275  play_replay();
276  break;
277  case HOTKEY_REPLAY_RESET:
278  reset_replay();
279  break;
280  case HOTKEY_REPLAY_STOP:
281  stop_replay();
282  break;
285  break;
288  break;
291  break;
294  break;
297  break;
300  break;
303  break;
304  case HOTKEY_REPLAY_EXIT:
305  replay_exit();
306  break;
307  case HOTKEY_WB_TOGGLE:
309  break;
312  break;
315  break;
318  break;
321  break;
324  break;
327  break;
328  case HOTKEY_SELECT_HEX:
329  select_hex();
330  break;
331  case HOTKEY_DESELECT_HEX:
332  deselect_hex();
333  break;
334  case HOTKEY_MOVE_ACTION:
335  move_action();
336  break;
339  break;
340  case HOTKEY_TOUCH_HEX:
341  touch_hex();
342  break;
343  case HOTKEY_ACCELERATED:
345  break;
346  case LUA_CONSOLE:
347  lua_console();
348  break;
349  case HOTKEY_ZOOM_IN:
350  zoom_in();
351  break;
352  case HOTKEY_ZOOM_OUT:
353  zoom_out();
354  break;
355  case HOTKEY_ZOOM_DEFAULT:
356  zoom_default();
357  break;
359  map_screenshot();
360  break;
363  break;
364  case HOTKEY_QUIT_GAME:
365  gui2::switch_theme(prefs::get().gui2_theme());
367  break;
368  case HOTKEY_SURRENDER:
369  surrender_game();
370  break;
372  prefs::get().set_minimap_draw_terrain(!prefs::get().minimap_draw_terrain());
374  break;
376  prefs::get().set_minimap_terrain_coding(!prefs::get().minimap_terrain_coding());
378  break;
380  prefs::get().set_minimap_movement_coding(!prefs::get().minimap_movement_coding());
382  break;
384  prefs::get().set_minimap_draw_units(!prefs::get().minimap_draw_units());
386  break;
388  prefs::get().set_minimap_draw_villages(!prefs::get().minimap_draw_villages());
390  break;
391  case HOTKEY_ACHIEVEMENTS:
392  {
394  ach.show();
395  }
396  break;
397  default:
398  return false;
399  }
400  return true;
401 }
402 
404  if(gui2::show_message(_("Surrender"), _("Do you really want to surrender the game?"), gui2::dialogs::message::yes_no_buttons) != gui2::retval::CANCEL) {
406  if(pmc && !pmc->is_linger_mode() && !pmc->is_observer()) {
408  }
409  }
410 }
411 
412 void command_executor::show_menu(const std::vector<config>& items_arg, int xloc, int yloc, bool /*context_menu*/, display& gui)
413 {
414  std::vector<config> items = items_arg;
415  if (items.empty()) return;
416 
417  get_menu_images(gui, items);
418 
419  int res = -1;
420  {
421  SDL_Rect pos {xloc, yloc, 1, 1};
422  gui2::dialogs::drop_down_menu mmenu(pos, items, -1, true, false); // TODO: last value should be variable
423  if(mmenu.show()) {
424  res = mmenu.selected_item();
425  }
426  } // This will kill the dialog.
427  if (res < 0 || std::size_t(res) >= items.size()) return;
428 
429  std::string id = items[res]["id"];
430  const theme::menu* submenu = gui.get_theme().get_menu_item(id);
431  if (submenu) {
432  auto [x, y] = sdl::get_mouse_location();
433  this->show_menu(submenu->items(), x, y, submenu->is_context(), gui);
434  } else {
435  hotkey::ui_command cmd = hotkey::ui_command(id, res);
436  do_execute_command(cmd);
438  }
439 }
440 
441 void command_executor::execute_action(const std::vector<std::string>& items_arg, int /*xloc*/, int /*yloc*/, bool /*context_menu*/, display&)
442 {
443  std::vector<std::string> items = items_arg;
444  if (items.empty()) {
445  return;
446  }
447 
448  std::vector<std::string>::iterator i = items.begin();
449  while(i != items.end()) {
451  if (can_execute_command(cmd)) {
452  do_execute_command(cmd);
454  }
455  ++i;
456  }
457 }
458 
459 std::string command_executor::get_menu_image(display& disp, const std::string& command, int index) const
460 {
461  const std::string base_image_name = "icons/action/" + command + "_25.png";
462  const std::string pressed_image_name = "icons/action/" + command + "_25-pressed.png";
463 
465  const hotkey::ACTION_STATE state = get_action_state(cmd);
466 
467  const theme::menu* menu = disp.get_theme().get_menu_item(command);
468  if (menu) {
469  return "icons/arrows/short_arrow_right_25.png~CROP(3,3,18,18)"; // TODO should not be hardcoded
470  }
471 
472  if (filesystem::file_exists(game_config::path + "/images/" + base_image_name)) {
473  switch (state) {
474  case ACTION_ON:
475  case ACTION_SELECTED:
476  return pressed_image_name + "~CROP(3,3,18,18)";
477  default:
478  return base_image_name + "~CROP(3,3,18,18)";
479  }
480  }
481 
482  switch (get_action_state(cmd)) {
483  case ACTION_ON:
485  case ACTION_OFF:
487  case ACTION_SELECTED:
489  case ACTION_DESELECTED:
491  default: return get_action_image(cmd);
492  }
493 }
494 
495 void command_executor::get_menu_images(display& disp, std::vector<config>& items)
496 {
497  for(std::size_t i = 0; i < items.size(); ++i) {
498  config& item = items[i];
499 
500  const std::string& item_id = item["id"];
502 
503  //see if this menu item has an associated image
504  std::string img(get_menu_image(disp, item_id, i));
505  if (img.empty() == false) {
506  item["icon"] = img;
507  }
508 
509  const theme::menu* menu = disp.get_theme().get_menu_item(item_id);
510  if(menu) {
511  item["label"] = menu->title();
512  } else if(hk != hotkey::HOTKEY_NULL) {
513  std::string desc = hotkey::get_hotkey_command(item_id).description;
514  if(hk == HOTKEY_ENDTURN) {
515  const theme::action *b = disp.get_theme().get_action_item("button-endturn");
516  if (b) {
517  desc = b->title();
518  }
519  }
520 
521  item["label"] = desc;
522  item["details"] = hotkey::get_names(item_id);
523  }
524  }
525 }
526 
527 void mbutton_event(const SDL_Event& event, command_executor* executor)
528 {
529  event_queue(event, executor);
530 
531  /* Run mouse events immediately.
532 
533  This is necessary because the sidebar doesn't allow set_button_state() to be called after a
534  button has received the mouse press event but before it has received the mouse release event.
535  When https://github.com/wesnoth/wesnoth/pull/2872 delayed the processing of input events,
536  set_button_state() ended up being called at such a time. However, if we run the event handlers
537  now, the button (if any) hasn't received the press event yet and we can call set_button_state()
538  safely.
539 
540  See https://github.com/wesnoth/wesnoth/issues/2884 */
541 
542  run_events(executor);
543 }
544 
545 void jbutton_event(const SDL_Event& event, command_executor* executor)
546 {
547  event_queue(event, executor);
548 }
549 
550 void jhat_event(const SDL_Event& event, command_executor* executor)
551 {
552  event_queue(event, executor);
553 }
554 
555 void key_event(const SDL_Event& event, command_executor* executor)
556 {
557  if (!executor) return;
558  event_queue(event,executor);
559 }
560 
561 void keyup_event(const SDL_Event&, command_executor* executor)
562 {
563  if(!executor) return;
564  executor->handle_keyup();
565 }
566 
568 {
569  if(!executor) return;
570  bool commands_ran = executor->run_queued_commands();
571  if(commands_ran) {
572  executor->set_button_state();
573  }
574 }
575 
576 static void event_queue(const SDL_Event& event, command_executor* executor)
577 {
578  if (!executor) return;
579  executor->queue_command(event);
580  executor->set_button_state();
581 }
582 
583 void command_executor::queue_command(const SDL_Event& event, int index)
584 {
585  LOG_HK << "event 0x" << std::hex << event.type << std::dec;
586  if(event.type == SDL_TEXTINPUT) {
587  LOG_HK << "SDL_TEXTINPUT \"" << event.text.text << "\"";
588  }
589 
590  const hotkey_ptr hk = get_hotkey(event);
591  if(!hk->active() || hk->is_disabled()) {
592  return;
593  }
594 
595  const hotkey_command& command = hotkey::get_hotkey_command(hk->get_command());
596  bool keypress = (event.type == SDL_KEYDOWN || event.type == SDL_TEXTINPUT) &&
598  bool press = keypress ||
599  (event.type == SDL_JOYBUTTONDOWN || event.type == SDL_MOUSEBUTTONDOWN || event.type == SDL_FINGERDOWN);
600  bool release = event.type == SDL_KEYUP;
601  if(press) {
602  LOG_HK << "sending press event (keypress = " <<
603  std::boolalpha << keypress << std::noboolalpha << ")";
604  }
605  if(keypress) {
606  press_event_sent_ = true;
607  }
608 
609  command_queue_.emplace_back(command, index, press, release);
610 }
611 
613 {
614  auto ui_cmd = hotkey::ui_command(*command.command, command.index);
615  if (!can_execute_command(ui_cmd)
616  || do_execute_command(ui_cmd, command.press, command.release)) {
617  return;
618  }
619 
620  if (!command.press) {
621  return; // none of the commands here respond to a key release
622  }
623 
624  switch(command.command->command) {
625  case HOTKEY_FULLSCREEN:
627  break;
628  case HOTKEY_SCREENSHOT:
629  make_screenshot(_("Screenshot"), false);
630  break;
631  case HOTKEY_ANIMATE_MAP:
632  prefs::get().set_animate_map(!prefs::get().animate_map());
633  break;
634  case HOTKEY_MOUSE_SCROLL:
635  prefs::get().set_mouse_scrolling(!prefs::get().mouse_scrolling());
636  break;
637  case HOTKEY_MUTE:
638  {
639  // look if both is not playing
640  static struct before_muted_s
641  {
642  bool playing_sound,playing_music;
643  before_muted_s() : playing_sound(false),playing_music(false){}
644  } before_muted;
645  if (prefs::get().music_on() || prefs::get().sound())
646  {
647  // then remember settings and mute both
648  before_muted.playing_sound = prefs::get().sound();
649  before_muted.playing_music = prefs::get().music_on();
650  prefs::get().set_sound(false);
651  prefs::get().set_music(false);
652  }
653  else
654  {
655  // then set settings before mute
656  prefs::get().set_sound(before_muted.playing_sound);
657  prefs::get().set_music(before_muted.playing_music);
658  }
659  }
660  break;
661  default:
662  DBG_G << "command_executor: unknown command number " << command.command->command << ", ignoring.";
663  break;
664  }
665 }
666 
668 {
669  display& disp = get_display();
670  for (const theme::menu& menu : disp.get_theme().menus()) {
671 
672  std::shared_ptr<gui::button> button = disp.find_menu_button(menu.get_id());
673  if (!button) continue;
674  bool enabled = false;
675  for (const auto& command : menu.items()) {
676 
677  ui_command command_obj = ui_command(command["id"].str());
678  bool can_execute = can_execute_command(command_obj);
679  if (can_execute) {
680  enabled = true;
681  break;
682  }
683  }
684  button->enable(enabled);
685  }
686 
687  for (const theme::action& action : disp.get_theme().actions()) {
688 
689  std::shared_ptr<gui::button> button = disp.find_action_button(action.get_id());
690  if (!button) continue;
691  bool enabled = false;
692  int i = 0;
693  for (const std::string& command : action.items()) {
694 
695  ui_command command_obj = ui_command(command);
696  std::string tooltip = action.tooltip(i);
697  if (filesystem::file_exists(game_config::path + "/images/icons/action/" + command + "_25.png" ))
698  button->set_overlay("icons/action/" + command);
699  if (!tooltip.empty())
700  button->set_tooltip_string(tooltip);
701 
702  bool can_execute = can_execute_command(command_obj);
703  i++;
704  if (!can_execute) continue;
705  enabled = true;
706 
707  ACTION_STATE state = get_action_state(command_obj);
708  switch (state) {
709  case ACTION_SELECTED:
710  case ACTION_ON:
711  button->set_check(true);
712  break;
713  case ACTION_OFF:
714  case ACTION_DESELECTED:
715  button->set_check(false);
716  break;
717  case ACTION_STATELESS:
718  break;
719  default:
720  break;
721  }
722 
723  break;
724  }
725  button->enable(enabled);
726  }
727 }
728 
729 // Removes duplicate commands caused by both SDL_KEYDOWN and SDL_TEXTINPUT triggering hotkeys.
730 // See https://github.com/wesnoth/wesnoth/issues/1736
731 std::vector<command_executor::queued_command> command_executor::filter_command_queue()
732 {
733  std::vector<queued_command> filtered_commands;
734 
735  /** A command plus "key released" flag. Otherwise, we will filter out key releases that are preceded by a keypress. */
736  using command_with_keyrelease = std::pair<const hotkey_command*, bool>;
737  std::set<command_with_keyrelease> seen_commands;
738 
739  for(const queued_command& cmd : command_queue_) {
740  command_with_keyrelease command_key(cmd.command, cmd.release);
741  if(seen_commands.find(command_key) == seen_commands.end()) {
742  seen_commands.insert(command_key);
743  filtered_commands.push_back(cmd);
744  }
745  }
746 
747  command_queue_.clear();
748 
749  return filtered_commands;
750 }
751 
753 {
754  std::vector<queued_command> commands = filter_command_queue();
755  for(const queued_command& cmd : commands) {
757  }
758 
759  return !commands.empty();
760 }
761 
763 {
765 }
766 
768 {
769  if (get_display().in_game()) {
771  } else {
773  }
774 
775 }
776 
778 {
780 }
781 
783 {
784  if(!get_display().view_locked()) {
785  get_display().set_zoom(true);
786  }
787 }
788 
790 {
791  if(!get_display().view_locked()) {
792  get_display().set_zoom(false);
793  }
794 }
795 
797 {
798  if(!get_display().view_locked()) {
800  }
801 }
802 
804 {
805  make_screenshot(_("Map-Screenshot"), true);
806 }
807 }
A config object defines a single node in a WML file, with access to child nodes.
Definition: config.hpp:172
Sort-of-Singleton that many classes, both GUI and non-GUI, use to access the game data.
Definition: display.hpp:97
void recalculate_minimap()
Schedule the minimap for recalculation.
Definition: display.cpp:1576
std::shared_ptr< gui::button > find_action_button(const std::string &id)
Retrieves a pointer to a theme UI button.
Definition: display.cpp:770
std::shared_ptr< gui::button > find_menu_button(const std::string &id)
Definition: display.cpp:780
bool set_zoom(bool increase)
Zooms the display in (true) or out (false).
Definition: display.cpp:1803
surface screenshot(bool map_screenshot=false)
Capture a (map-)screenshot into a surface.
Definition: display.cpp:725
theme & get_theme()
Definition: display.hpp:390
void toggle_default_zoom()
Sets the zoom amount to the default.
Definition: display.cpp:1871
static display * get_singleton()
Returns the display object if a display object exists.
Definition: display.hpp:111
std::size_t viewing_team_index() const
The viewing team is the team currently viewing the game.
Definition: display.hpp:126
Used by the menu_button widget.
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()
void get_menu_images(display &, std::vector< config > &items)
virtual bool do_execute_command(const hotkey::ui_command &command, bool press=true, bool release=false)
virtual void whiteboard_execute_action()
void execute_action(const std::vector< std::string > &items_arg, int xloc, int yloc, bool context_menu, display &gui)
virtual void show_enemy_moves(bool)
std::vector< queued_command > command_queue_
std::string get_menu_image(display &disp, const std::string &command, int index=-1) const
virtual ACTION_STATE get_action_state(const hotkey::ui_command &) const
virtual void toggle_shroud_updates()
virtual void whiteboard_bump_down_action()
void execute_command_wrap(const queued_command &command)
virtual void whiteboard_delete_action()
virtual void replay_show_everything()
virtual void toggle_accelerated_speed()
virtual void whiteboard_suppose_dead()
virtual void show_menu(const std::vector< config > &items_arg, int xloc, int yloc, bool context_menu, display &gui)
virtual void scroll_down(bool)
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 std::string get_action_image(const hotkey::ui_command &) const
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)
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()
const std::string & title() const
Definition: theme.hpp:229
bool is_context() const
Definition: theme.hpp:227
const std::vector< config > & items() const
Definition: theme.hpp:237
const action * get_action_item(const std::string &key) const
Definition: theme.cpp:926
const menu * get_menu_item(const std::string &key) const
Definition: theme.cpp:917
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:1029
static std::string _(const char *str)
Definition: gettext.hpp:93
std::string tooltip
Shown when hovering over an entry in the filter's drop-down list.
Definition: manager.cpp:202
Contains functions for cleanly handling SDL input.
Standard logging facilities (interface).
static bool file_exists(const bfs::path &fpath)
Definition: filesystem.cpp:326
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:586
std::string selected_menu
std::string deselected_menu
std::string unchecked_menu
std::string checked_menu
std::string path
Definition: filesystem.cpp:91
static void make_screenshot()
static bool sound()
static bool music_on()
void switch_theme(const std::string &current_theme)
Set and activate the given gui2 theme.
Definition: gui.cpp:135
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
General purpose widgets.
void show_help(const std::string &show_topic)
Open the help browser, show topic with id show_topic.
Definition: help.cpp:140
Keyboard shortcuts for game actions.
void jhat_event(const SDL_Event &event, command_executor *executor)
const hotkey_command & get_hotkey_command(const std::string &command)
returns the hotkey_command with the given name
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)
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
std::string img(const std::string &src, const std::string &align, const bool floating)
Definition: markup.cpp:29
play_controller * controller
Definition: resources.cpp:21
point get_mouse_location()
Returns the current mouse location in draw space.
Definition: input.cpp:54
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:803
std::string::const_iterator iterator
Definition: tokenizer.hpp:25
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 paramneter for can_execute_command/do_execute_command These functions are used to ex...
hotkey::HOTKEY_COMMAND hotkey_command
The hotkey::HOTKEY_COMMAND associated with this action, HOTKEY_NULL for actions that don't allow hotk...
#define b