The Battle for Wesnoth  1.17.21+dev
gamestate_inspector.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2009 - 2023
3  by Yurii Chernyi <terraninfo@terraninfo.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 
16 #define GETTEXT_DOMAIN "wesnoth-lib"
17 
19 
23 #include "gui/widgets/button.hpp"
24 #include "gui/widgets/label.hpp"
27 #include "gui/widgets/settings.hpp"
28 #include "gui/widgets/window.hpp"
29 
30 #include "desktop/clipboard.hpp"
31 #include "font/text_formatting.hpp"
32 #include "game_events/manager.hpp"
33 #include "serialization/parser.hpp" // for write()
34 
35 #include "game_board.hpp"
36 #include "game_data.hpp"
37 #include "gettext.hpp"
38 #include "recall_list_manager.hpp"
39 #include "team.hpp"
40 #include "units/unit.hpp"
41 #include "units/map.hpp"
42 #include "ai/manager.hpp"
43 
44 #include "display_context.hpp"
45 #include "filter_context.hpp"
46 
47 #include <vector>
48 #include <functional>
49 
50 namespace
51 {
52 
53 inline std::string config_to_string(const config& cfg)
54 {
55  std::ostringstream s;
56  write(s, cfg);
57  return s.str();
58 }
59 
60 inline std::string config_to_string(const config& cfg, std::string only_children)
61 {
62  config filtered;
63  for(const config& child : cfg.child_range(only_children)) {
64  filtered.add_child(only_children, child);
65  }
66  return config_to_string(filtered);
67 }
68 
69 }
70 
71 namespace gui2::dialogs
72 {
73 
75 {
76 public:
77  std::string name;
78 
79  std::string get_data_full() const
80  {
81  return data;
82  }
83 
84  std::string get_data_paged(int which_page)
85  {
86  if(std::size_t(which_page) >= pages.size()) {
87  return "";
88  }
89  return data.substr(pages[which_page].first, pages[which_page].second);
90  }
91 
92  void clear_data()
93  {
94  data.clear();
95  pages.clear();
96  }
97 
98  void set_data(const std::string& new_data)
99  {
100  data = new_data;
101  repaginate();
102  }
103 
105  {
106  return std::max<int>(pages.size(), 1);
107  }
108 
109 private:
110  void repaginate()
111  {
112  pages.clear();
113  std::size_t start = 0;
114  while(start + max_inspect_win_len < data.size()) {
115  // This could search into data that's already on a previous page, which is why the result
116  // is then checked for end < start.
117  std::size_t end = data.find_last_of('\n', start + max_inspect_win_len);
118  int len;
119  if(end == std::string::npos || end < start) {
120  len = max_inspect_win_len;
121  } else {
122  len = end - start + 1;
123  }
124  pages.emplace_back(start, len);
125  start += len;
126  }
127  if(start < data.size()) {
128  pages.emplace_back(start, data.size() - start);
129  }
130  }
131  static const unsigned int max_inspect_win_len = 20000;
132  std::string data;
133  std::vector<std::pair<std::size_t,int>> pages;
134 };
135 
137 {
138 public:
139  stuff_list_adder(tree_view_node& stuff_list, const std::string& defn)
140  : stuff_list_(stuff_list)
141  , defn_(defn)
142  {
143  }
144 
145  std::vector<int> add()
146  {
148  }
149 
150  stuff_list_adder& widget(const std::string& ref, const std::string& label, bool markup = false)
151  {
152  widget_item& item = data_[ref];
153  item["label"] = label;
154  item["use_markup"] = utils::bool_string(markup);
155  return *this;
156  }
157 
158 private:
160  const std::string defn_;
162 };
163 
165 {
166 public:
168  : stuff_list_(find_widget<tree_view>(&window, "stuff_list", false, true))
169  , inspect_(find_widget<styled_widget>(&window, "inspect", false, true))
170  , pages_(find_widget<styled_widget>(&window, "page_count", false, true))
171  , left_(find_widget<styled_widget>(&window, "page_left", false, true))
172  , right_(find_widget<styled_widget>(&window, "page_right", false, true))
173  {
174  }
175 
177  {
179  }
180 
181  void update(model& m)
182  {
183  int n_pages = m.count_pages();
184  current_page_ = std::min(n_pages - 1, std::max(0, current_page_));
186  if(n_pages > 1) {
187  std::ostringstream out;
188  out << current_page_ + 1 << '/' << n_pages;
189  pages_->set_label(out.str());
192  } else {
193  pages_->set_label("");
196  }
197  }
198 
200  {
201  stuff_list_->clear();
202  pages_->set_label("");
205  }
206 
207  void page(int where)
208  {
209  current_page_ += where;
210  }
211 
212 private:
213  int current_page_ = 0;
219 };
220 
222 {
223 public:
225  {
226  }
227 
229  {
230  }
231 
232 protected:
236  const config& vars() const;
237  const game_events::manager& events() const;
238  const display_context& dc() const;
239 };
240 
242 {
243 public:
246  {
247  }
248 
249  void show_list(tree_view_node& node);
250  void show_var(tree_view_node& node);
251  void show_array(tree_view_node& node);
252 };
253 
255 {
256 public:
258  void show_list(tree_view_node& node, bool is_wmi);
259  void show_event(tree_view_node& node, bool is_wmi);
260 
261 private:
263 };
264 
266 {
267 public:
270  {
271  }
272 
273  void show_list(tree_view_node& node);
274  void show_unit(tree_view_node& node);
275  void show_var(tree_view_node& node);
276  void show_array(tree_view_node& node);
277 };
278 
280 {
281 public:
284  {
285  }
286 
287  void show_list(tree_view_node& node, int side);
288  void show_ai(tree_view_node& node, int side);
289  void show_ai_components(tree_view_node& node, int side);
290  void show_ai_tree(tree_view_node& node, int side);
291  void show_recall(tree_view_node& node, int side);
292  void show_recall_unit(tree_view_node& node, int side);
293  void show_units(tree_view_node& node, int side);
294  void show_unit(tree_view_node& node, int side);
295  void show_vars(tree_view_node& node, int side);
296  void show_var(tree_view_node& node, int side);
297  void show_array(tree_view_node& node, int side);
298 };
299 
301 {
303 public:
304  controller(model& m, view& v, const config& vars, const game_events::manager& events, const display_context& dc)
305  : model_(m), view_(v)
306  , vars_(vars), events_(events), dc_(dc)
307  {
308  }
309 
311  {
312  tree_view_node* selected = dynamic_cast<tree_view&>(tree).selected_item();
313  callbacks[selected->describe_path()](*selected);
314 
315  // We recursively fold, but non-recursively unfold.
316  // This is because only one node on a level should be open at any given time.
317  // Furthermore, there's no need to remember that a subnode was open once the parent is closed.
318  if(!selected->is_root_node()) {
319  for(auto& node : selected->parent_node().children()) {
320  if(node.get() != selected) {
321  node->fold(true);
322  }
323  }
324 
325  selected->unfold();
326  }
327 
329  }
330 
332  {
334  }
335 
337  {
339  // The game state could've changed, so reset the dialog
340  callbacks.clear();
341  controllers.clear();
344  model_.clear_data();
346  }
347 
349  {
350  view_.page(next ? 1 : -1);
352  }
353 
354  template<typename T>
355  std::shared_ptr<T> get_controller()
356  {
357  for(auto& c : controllers) {
358  if(std::shared_ptr<T> p = std::dynamic_pointer_cast<T>(c)) {
359  return p;
360  }
361  }
362  std::shared_ptr<T> p = std::make_shared<T>(*this);
363  controllers.push_back(p);
364  return p;
365  }
366 
367  template<typename C>
368  void set_node_callback(const std::vector<int>& node_path, void (C::* fcn)(tree_view_node&))
369  {
370  C& sub_controller = *get_controller<C>();
371  callbacks.emplace(node_path, std::bind(fcn, sub_controller, std::placeholders::_1));
372  }
373 
374  template<typename C, typename T>
375  void set_node_callback(const std::vector<int>& node_path, void (C::* fcn)(tree_view_node&, T), T param)
376  {
377  C& sub_controller = *get_controller<C>();
378  callbacks.emplace(node_path, std::bind(fcn, sub_controller, std::placeholders::_1, param));
379  }
380 
382  {
383  auto stuff_list = find_widget<tree_view>(&window, "stuff_list", false, true);
384  auto copy_button = find_widget<button>(&window, "copy", false, true);
385  auto lua_button = find_widget<button>(&window, "lua", false, true);
386  auto left_button = find_widget<button>(&window, "page_left", false, true);
387  auto right_button = find_widget<button>(&window, "page_right", false, true);
388 
389  connect_signal_notify_modified(*stuff_list,
390  std::bind(&gamestate_inspector::controller::handle_stuff_list_item_clicked, this, std::placeholders::_1));
391 
393  *copy_button,
395  this));
396 
398  *lua_button,
400  this, std::ref(window)));
401 
403  *left_button,
405  this, false));
406 
408  *right_button,
410  this, true));
411 
412  left_button->set_visible(widget::visibility::invisible);
413  right_button->set_visible(widget::visibility::invisible);
414 
416  copy_button->set_active(false);
417  copy_button->set_tooltip(_("Clipboard support not found, contact your packager"));
418  }
419 
421  }
422 
424  {
426  view_.stuff_list_entry(nullptr, "basic")
427  .widget("name", "variables")
428  .add(),
431  view_.stuff_list_entry(nullptr, "basic")
432  .widget("name", "events")
433  .add(),
435  false);
437  view_.stuff_list_entry(nullptr, "basic")
438  .widget("name", "menu items")
439  .add(),
441  true);
443  view_.stuff_list_entry(nullptr, "basic")
444  .widget("name", "units")
445  .add(),
447  int sides = dc_.teams().size();
448  for(int side = 1; side <= sides; side++) {
449  std::ostringstream label;
450  label << "team " << side;
451  const std::string& name = dc_.get_team(side).user_team_name();
452  if(!name.empty()) {
453  label << " (" << name << ")";
454  }
456  view_.stuff_list_entry(nullptr, "basic")
457  .widget("name", label.str())
458  .add(),
460  side);
461  }
462  // Expand initially selected node
463  callbacks[{0}](find_widget<tree_view>(&window, "stuff_list", false).get_root_node().get_child_at(0));
464  }
465 
466 private:
469  using node_callback = std::function<void(tree_view_node&)>;
470  using node_callback_map = std::map<std::vector<int>, node_callback>;
471  std::vector<std::shared_ptr<single_mode_controller>> controllers;
473  const config& vars_;
476 };
477 
479  return c.model_;
480 }
481 
483  return c.view_;
484 }
485 
487  return c.vars_;
488 }
489 
491  return c.events_;
492 }
493 
495  return c.dc_;
496 }
497 
500 {
502 }
503 
505 {
506  model().clear_data();
507 
508  if(node.count_children() > 0) {
509  return;
510  }
511 
512  for(const auto& attr : vars().attribute_range())
513  {
515  view().stuff_list_entry(&node, "basic")
516  .widget("name", attr.first)
517  .add(),
519  }
520 
521  std::map<std::string, std::size_t> wml_array_sizes;
522 
523  for(const auto ch : vars().all_children_range())
524  {
525 
526  std::ostringstream cur_str;
527  cur_str << "[" << ch.key << "][" << wml_array_sizes[ch.key] << "]";
528 
529  this->c.set_node_callback(
530  view().stuff_list_entry(&node, "basic")
531  .widget("name", cur_str.str())
532  .add(),
534  wml_array_sizes[ch.key]++;
535  }
536 }
537 
539 {
540  widget* w = node.find("name", false);
541  if(label* lbl = dynamic_cast<label*>(w)) {
542  model().set_data(vars()[lbl->get_label().str()]);
543  }
544 }
545 
547 {
548  widget* w = node.find("name", false);
549  if(label* lbl = dynamic_cast<label*>(w)) {
550  const std::string& var = lbl->get_label();
551  std::size_t n_start = var.find_last_of('[') + 1;
552  std::size_t n_len = var.size() - n_start - 1;
553  int n = std::stoi(var.substr(n_start, n_len));
554  model().set_data(config_to_string(vars().mandatory_child(var.substr(1, n_start - 3), n)));
555  }
556 }
557 
559 {
560  model().clear_data();
561 
562  if(node.count_children() > 0) {
563  return;
564  }
565 
566  for(const auto & cfg : events.child_range(is_wmi ? "menu_item" : "event"))
567  {
568  std::string name = is_wmi ? cfg["id"] : cfg["name"];
569  bool named_event = !is_wmi && !cfg["id"].empty();
570 
571  auto progress = view()
572  .stuff_list_entry(&node, named_event ? "named_event" : "basic")
573  .widget("name", name);
574 
575  if(named_event) {
576  std::ostringstream out;
577  out << "id=\"" << cfg["id"] << '"';
578  progress.widget("id", out.str());
579  }
580 
581  c.set_node_callback(progress.add(), &event_mode_controller::show_event, is_wmi);
582  }
583 
584 }
585 
587 {
588  int n = node.describe_path().back();
589  model().set_data(config_to_string(events.mandatory_child(is_wmi ? "menu_item" : "event", n)));
590 }
591 
593 {
594 
595  color_t team_color = game_config::tc_info(dc.get_team(u.side()).color())[0];
596  std::stringstream s;
597 
598  s << '(' << u.get_location() << ')';
599  progress.widget("loc", s.str());
600 
601  s.str("");
602  s << font::span_color(team_color);
603  s << "side=" << u.side() << "</span>";
604  progress.widget("side", s.str(), true);
605 
606  if(u.can_recruit()) {
607  progress.widget("leader", "<span color='yellow'>LEADER</span> ", true);
608  }
609 
610  s.str("");
611  s << "id=\"" << u.id() << '"';
612  progress.widget("id", s.str());
613 
614  progress.widget("type", u.type_id());
615 
616  s.str("");
617  s << "L" << u.level();
618  progress.widget("level", s.str());
619 
620  s.str("");
621  s << u.experience() << '/' << u.max_experience() << " xp";
622  progress.widget("xp", s.str());
623 
624  s.str("");
625  s << u.hitpoints() << '/' << u.max_hitpoints() << " hp";
626  progress.widget("hp", s.str());
627 
628  progress.widget("traits", utils::join(u.get_traits_list(), ", "));
629 
630  return progress;
631 }
632 
634 {
635  model().clear_data();
636 
637  if(node.count_children() > 0) {
638  return;
639  }
640 
641  for(unit_map::const_iterator i = dc().units().begin(); i != dc().units().end(); ++i) {
642  auto progress = view().stuff_list_entry(&node, "unit");
643  add_unit_entry(progress, *i, dc());
645  }
646 }
647 
649 {
650  int i = node.describe_path().back();
652  std::advance(u, i);
653  config c_unit;
654  u->write(c_unit);
655  model().set_data(config_to_string(c_unit));
656 
657  if(node.count_children() > 0) {
658  return;
659  }
660 
661  for(const auto& attr : u->variables().attribute_range())
662  {
664  view().stuff_list_entry(&node, "basic")
665  .widget("name", attr.first)
666  .add(),
668  }
669 
670  std::map<std::string, std::size_t> wml_array_sizes;
671 
672  for(const auto ch : u->variables().all_children_range())
673  {
674 
675  std::ostringstream cur_str;
676  cur_str << "[" << ch.key << "][" << wml_array_sizes[ch.key] << "]";
677 
678  this->c.set_node_callback(
679  view().stuff_list_entry(&node, "basic")
680  .widget("name", cur_str.str())
681  .add(),
683  wml_array_sizes[ch.key]++;
684  }
685 }
686 
688 {
689  widget* w = node.find("name", false);
690  int i = node.describe_path().back();
692  std::advance(u, i);
693  if(label* lbl = dynamic_cast<label*>(w)) {
694  model().set_data(u->variables()[lbl->get_label().str()]);
695  }
696 }
697 
699 {
700  widget* w = node.find("name", false);
701  int i = node.describe_path().back();
703  std::advance(u, i);
704  if(label* lbl = dynamic_cast<label*>(w)) {
705  const std::string& var = lbl->get_label();
706  std::size_t n_start = var.find_last_of('[') + 1;
707  std::size_t n_len = var.size() - n_start - 1;
708  int n = std::stoi(var.substr(n_start, n_len));
709  model().set_data(config_to_string(u->variables().mandatory_child(var.substr(1, n_start - 3), n)));
710  }
711 }
712 
714 {
715  config&& cfg = dc().get_team(side).to_config();
716  cfg.clear_children("ai");
717  model().set_data(config_to_string(cfg));
718 
719  if(node.count_children() > 0) {
720  return;
721  }
722 
724  view().stuff_list_entry(&node, "basic")
725  .widget("name", "ai")
726  .add(),
728  side);
730  view().stuff_list_entry(&node, "basic")
731  .widget("name", "recall list")
732  .add(),
734  side);
736  view().stuff_list_entry(&node, "basic")
737  .widget("name", "units")
738  .add(),
740  side);
742  view().stuff_list_entry(&node, "basic")
743  .widget("name", "variables")
744  .add(),
746  side);
747 }
748 
750 {
751  model().set_data(ai::manager::get_singleton().get_active_ai_overview_for_side(side));
752 
753  if(node.count_children() > 0) {
754  return;
755  }
756 
758  view().stuff_list_entry(&node, "basic")
759  .widget("name", "engines")
760  .add(),
762  side);
764  view().stuff_list_entry(&node, "basic")
765  .widget("name", "stages")
766  .add(),
768  side);
770  view().stuff_list_entry(&node, "basic")
771  .widget("name", "aspects")
772  .add(),
774  side);
776  view().stuff_list_entry(&node, "basic")
777  .widget("name", "goals")
778  .add(),
780  side);
782  view().stuff_list_entry(&node, "basic")
783  .widget("name", "component structure")
784  .add(),
786  side);
787 }
788 
790 {
791  widget* w = node.find("name", false);
792  if(label* lbl = dynamic_cast<label*>(w)) {
793  std::string tag = lbl->get_label();
794  tag.pop_back();
795  model().set_data(config_to_string(ai::manager::get_singleton().to_config(side), tag));
796  }
797 }
798 
800 {
801  model().clear_data();
802 
803  if(node.count_children() > 0) {
804  return;
805  }
806 
807  for(const unit_ptr& u : dc().get_team(side).recall_list()) {
808  auto progress = view().stuff_list_entry(&node, "unit");
809  add_unit_entry(progress, *u, dc());
811  }
812 }
813 
815 {
816  int i = node.describe_path().back();
817  auto u = dc().get_team(side).recall_list().begin();
818  std::advance(u, i);
819  config c_unit;
820  (*u)->write(c_unit);
821  model().set_data(config_to_string(c_unit));
822 }
823 
825 {
826  model().set_data(ai::manager::get_singleton().get_active_ai_structure_for_side(side));
827 }
828 
830 {
831  std::ostringstream s;
832  for(unit_map::const_iterator i = dc().units().begin(); i != dc().units().end();
833  ++i) {
834  if(i->side() != side) {
835  continue;
836  }
837  s << '(' << i->get_location() << ") ";
838  if(i->can_recruit()) {
839  s << "LEADER ";
840  }
841 
842  s << "\nid=\"" << i->id() << "\" (" << i->type_id() << ")\n"
843  << "L" << i->level() << "; " << i->experience() << '/'
844  << i->max_experience() << " XP; " << i->hitpoints() << '/'
845  << i->max_hitpoints() << " HP\n";
846  for(const auto & str : i->get_traits_list())
847  {
848  s << "\t" << str << std::endl;
849  }
850  s << std::endl;
851  }
852  model().set_data(s.str());
853 }
854 
856 {
857  model().clear_data();
858 
859  if(node.count_children() > 0) {
860  return;
861  }
862 
863  const team& t = dc().get_team(side);
864 
865  for(const auto& attr : t.variables().attribute_range())
866  {
868  view().stuff_list_entry(&node, "basic")
869  .widget("name", attr.first)
870  .add(),
872  side);
873  }
874 
875  std::map<std::string, std::size_t> wml_array_sizes;
876 
877  for(const auto ch : t.variables().all_children_range())
878  {
879 
880  std::ostringstream cur_str;
881  cur_str << "[" << ch.key << "][" << wml_array_sizes[ch.key] << "]";
882 
883  this->c.set_node_callback(
884  view().stuff_list_entry(&node, "basic")
885  .widget("name", cur_str.str())
886  .add(),
888  side);
889  wml_array_sizes[ch.key]++;
890  }
891 }
892 
894 {
895  widget* w = node.find("name", false);
896  const team& t = dc().get_team(side);
897  if(label* lbl = dynamic_cast<label*>(w)) {
898  model().set_data(t.variables()[lbl->get_label().str()]);
899  }
900 }
901 
903 {
904  widget* w = node.find("name", false);
905  const team& t = dc().get_team(side);
906  if(label* lbl = dynamic_cast<label*>(w)) {
907  const std::string& var = lbl->get_label();
908  std::size_t n_start = var.find_last_of('[') + 1;
909  std::size_t n_len = var.size() - n_start - 1;
910  int n = std::stoi(var.substr(n_start, n_len));
911  model().set_data(config_to_string(t.variables().mandatory_child(var.substr(1, n_start - 3), n)));
912  }
913 }
914 
916 
917 gamestate_inspector::gamestate_inspector(const config& vars, const game_events::manager& events, const display_context& dc, const std::string& title)
918  : modal_dialog(window_id())
919  , title_(title)
920  , vars_(vars)
921  , events_(events)
922  , dc_(dc)
923 {
924  model_.reset(new model);
925 }
926 
928 {
929  view_.reset(new view(window));
930  controller_.reset(new controller(*model_, *view_, vars_, events_, dc_));
931 
932  if(!title_.empty()) {
933  find_widget<styled_widget>(&window, "inspector_name", false).set_label(title_);
934  }
935  controller_->bind(window);
936  view_->update(*model_);
937 }
938 
939 } // namespace dialogs
Managing the AIs lifecycle - headers TODO: Refactor history handling and internal commands.
double t
Definition: astarsearch.cpp:65
static manager & get_singleton()
Definition: manager.hpp:145
A config object defines a single node in a WML file, with access to child nodes.
Definition: config.hpp:161
void clear_children(T... keys)
Definition: config.hpp:644
child_itors child_range(config_key_type key)
Definition: config.cpp:277
config & add_child(config_key_type key)
Definition: config.cpp:445
Abstract class for exposing game data that doesn't depend on the GUI, however which for historical re...
const team & get_team(int side) const
This getter takes a 1-based side number, not a 0-based team number.
virtual const std::vector< team > & teams() const =0
virtual const unit_map & units() const =0
The game event manager loads the scenario configuration object, and ensures that events are handled a...
Definition: manager.hpp:47
void write_events(config &cfg, bool include_nonserializable=false) const
Definition: manager.cpp:175
grid::iterator end()
void show_list(tree_view_node &node, bool is_wmi)
void show_event(tree_view_node &node, bool is_wmi)
event_mode_controller(gamestate_inspector::controller &c)
std::map< std::vector< int >, node_callback > node_callback_map
void set_node_callback(const std::vector< int > &node_path, void(C::*fcn)(tree_view_node &, T), T param)
controller(model &m, view &v, const config &vars, const game_events::manager &events, const display_context &dc)
std::vector< std::shared_ptr< single_mode_controller > > controllers
std::function< void(tree_view_node &)> node_callback
void set_node_callback(const std::vector< int > &node_path, void(C::*fcn)(tree_view_node &))
void set_data(const std::string &new_data)
std::vector< std::pair< std::size_t, int > > pages
stuff_list_adder stuff_list_entry(tree_view_node *parent, const std::string &defn)
This shows the gamestate inspector.
const game_events::manager & events_
virtual void pre_show(window &window) override
Actions to be taken before showing the window.
std::shared_ptr< controller > controller_
static void display(lua_kernel_base *lk)
Display a new console, using given video and lua kernel.
Abstract base class for all modal dialogs.
const game_events::manager & events() const
single_mode_controller(gamestate_inspector::controller &c)
gamestate_inspector::controller & c
const display_context & dc() const
gamestate_inspector::model & model()
stuff_list_adder(tree_view_node &stuff_list, const std::string &defn)
stuff_list_adder & widget(const std::string &ref, const std::string &label, bool markup=false)
void show_var(tree_view_node &node, int side)
void show_ai_tree(tree_view_node &node, int side)
void show_ai(tree_view_node &node, int side)
void show_vars(tree_view_node &node, int side)
void show_recall(tree_view_node &node, int side)
void show_unit(tree_view_node &node, int side)
void show_array(tree_view_node &node, int side)
void show_ai_components(tree_view_node &node, int side)
void show_units(tree_view_node &node, int side)
void show_list(tree_view_node &node, int side)
team_mode_controller(gamestate_inspector::controller &c)
void show_recall_unit(tree_view_node &node, int side)
unit_mode_controller(gamestate_inspector::controller &c)
variable_mode_controller(gamestate_inspector::controller &c)
A label displays text that can be wrapped but no scrollbars are provided.
Definition: label.hpp:57
Base class for all visible items.
virtual void set_label(const t_string &label)
std::vector< int > describe_path()
Calculates the node indices needed to get from the root node to this node.
widget * find(const std::string &id, const bool must_be_active) override
See widget::find.
std::size_t count_children() const
The number of children in this widget.
tree_view_node & add_child(const std::string &id, const widget_data &data, const int index=-1)
Constructs a new child node.
A tree view is a control that holds several items of the same or different types.
Definition: tree_view.hpp:61
tree_view_node & get_root_node()
Definition: tree_view.hpp:75
Base class for all widgets.
Definition: widget.hpp:54
void set_visible(const visibility visible)
Definition: widget.cpp:456
@ visible
The user sets the widget visible, that means:
@ invisible
The user set the widget invisible, that means:
widget * parent()
Definition: widget.cpp:161
base class of top level items, the only item which needs to store the final canvases to draw on.
Definition: window.hpp:67
iterator begin()
begin iterator
This class stores all the data for a single 'side' (in game nomenclature).
Definition: team.hpp:76
const std::string & color() const
Definition: team.hpp:244
config to_config() const
Definition: team.cpp:1046
recall_list_manager & recall_list()
Definition: team.hpp:203
const t_string & user_team_name() const
Definition: team.hpp:285
unit_iterator end()
Definition: map.hpp:429
unit_iterator begin()
Definition: map.hpp:419
This class represents a single unit of a specific type.
Definition: unit.hpp:134
std::size_t i
Definition: function.cpp:968
int w
static std::string _(const char *str)
Definition: gettext.hpp:93
int max_hitpoints() const
The max number of hitpoints this unit can have.
Definition: unit.hpp:506
int level() const
The current level of this unit.
Definition: unit.hpp:560
int hitpoints() const
The current number of hitpoints this unit has.
Definition: unit.hpp:500
const std::string & type_id() const
The id of this unit's type.
Definition: unit.cpp:1935
int experience() const
The current number of experience points this unit has.
Definition: unit.hpp:524
bool can_recruit() const
Whether this unit can recruit other units - ie, are they a leader unit.
Definition: unit.hpp:613
const std::string & id() const
Gets this unit's id.
Definition: unit.hpp:381
int side() const
The side this unit belongs to.
Definition: unit.hpp:344
int max_experience() const
The max number of experience points this unit can have.
Definition: unit.hpp:530
const map_location & get_location() const
The current map location this unit is at.
Definition: unit.hpp:1358
std::vector< std::string > get_traits_list() const
Gets a list of the traits this unit currently has.
Definition: unit.cpp:873
std::string label
What to show in the filter's drop-down list.
Definition: manager.cpp:217
This file contains the window object, this object is a top level container which has the event manage...
#define REGISTER_DIALOG(window_id)
Wrapper for REGISTER_DIALOG2.
void copy_to_clipboard(const std::string &text, const bool)
Copies text to the clipboard.
Definition: clipboard.cpp:34
bool available()
Whether wesnoth was compiled with support for a clipboard.
Definition: clipboard.cpp:55
EXIT_STATUS start(bool clear_id, const std::string &filename, bool take_screenshot, const std::string &screenshot_filename)
Main interface for launching the editor from the title screen.
Handling of system events.
Definition: manager.hpp:43
std::string span_color(const color_t &color)
Returns a Pango formatting string using the provided color_t object.
std::string selected
const std::vector< color_t > & tc_info(const std::string &name)
Domain specific events.
static stuff_list_adder add_unit_entry(stuff_list_adder &progress, const unit &u, const display_context &dc)
void connect_signal_notify_modified(dispatcher &dispatcher, const signal_notification &signal)
Connects a signal handler for getting a notification upon modification.
Definition: dispatcher.cpp:205
void connect_signal_mouse_left_click(dispatcher &dispatcher, const signal &signal)
Connects a signal handler for a left mouse button click.
Definition: dispatcher.cpp:179
std::map< std::string, widget_item > widget_data
Definition: widget.hpp:35
std::map< std::string, t_string > widget_item
Definition: widget.hpp:32
T * find_widget(utils::const_clone_ptr< widget, T > widget, const std::string &id, const bool must_be_active, const bool must_exist)
Gets a widget with the wanted id.
Definition: find_widget.hpp:69
std::pair< std::string, unsigned > item
Definition: help_impl.hpp:414
std::string bool_string(const bool value)
Converts a bool value to 'true' or 'false'.
std::string join(const T &v, const std::string &s=",")
Generates a new string joining container items in a list.
std::shared_ptr< unit > unit_ptr
Definition: ptr.hpp:26
void write(std::ostream &out, const configr_of &cfg, unsigned int level)
Definition: parser.cpp:764
This file contains the settings handling of the widget library.
The basic class for representing 8-bit RGB or RGBA colour values.
Definition: color.hpp:59
mock_char c
mock_party p
static map_location::DIRECTION n
static map_location::DIRECTION s