The Battle for Wesnoth  1.19.0-dev
game_version_dialog.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2013 - 2024
3  by Iris Morelle <shadowm2006@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 #define GETTEXT_DOMAIN "wesnoth-lib"
17 
19 
20 #include "build_info.hpp"
21 #include "desktop/clipboard.hpp"
22 #include "desktop/open.hpp"
23 #include "desktop/version.hpp"
24 #include "filesystem.hpp"
25 #include "formula/string_utils.hpp"
27 #include "gui/widgets/button.hpp"
29 #include "gui/widgets/listbox.hpp"
32 #include "gui/widgets/window.hpp"
33 
34 #include <functional>
35 
36 namespace
37 {
38 
39 const std::string text_feature_on = "<span color='#0f0'>&#9679;</span>";
40 const std::string text_feature_off = "<span color='#f00'>&#9679;</span>";
41 
42 } // end anonymous namespace
43 
44 namespace gui2::dialogs
45 {
46 
47 REGISTER_DIALOG(game_version)
48 
50  : modal_dialog(window_id())
51  , path_wid_stem_("path_")
52  , copy_wid_stem_("copy_")
53  , browse_wid_stem_("browse_")
54  , path_map_()
55  , log_path_(lg::get_log_file_path())
56  , deps_()
58  , report_()
59 {
60  // NOTE: these path_map_ entries are referenced by the GUI2 WML
61  // definition of this dialog using preprocessor macros.
62  path_map_["datadir"] = game_config::path;
63  path_map_["config"] = filesystem::get_user_config_dir();
64  path_map_["userdata"] = filesystem::get_user_data_dir();
65  path_map_["saves"] = filesystem::get_saves_dir();
66  path_map_["addons"] = filesystem::get_addons_dir();
67  path_map_["cache"] = filesystem::get_cache_dir();
68  // path to logs directory
69  path_map_["logs"] = filesystem::get_logs_dir();
70  path_map_["screenshots"] = filesystem::get_screenshot_dir();
71 
72  for(unsigned k = 0; k < game_config::LIB_COUNT; ++k) {
74 
76  e[0] = game_config::library_name(lib);
77  if(e[0].empty()) {
78  continue;
79  }
82  deps_.push_back(e);
83  }
84 
85  generate_plain_text_report();
86 }
87 
89 {
90  utils::string_map i18n_syms;
91 
92  //
93  // General information.
94  //
95 
96  styled_widget& version_label = find_widget<styled_widget>(&window, "version", false);
97  i18n_syms["version"] = game_config::revision + " " + game_config::build_arch();
98  version_label.set_label(VGETTEXT("Version $version", i18n_syms));
99 
100  styled_widget& os_label = find_widget<styled_widget>(&window, "os", false);
101  i18n_syms["os"] = desktop::os_version();
102  os_label.set_label(VGETTEXT("Running on $os", i18n_syms));
103 
104  button& copy_all = find_widget<button>(&window, "copy_all", false);
106 
107  //
108  // Game paths tab.
109  //
110 
111  for(const auto & path_ent : path_map_)
112  {
113  const std::string& path_id = path_ent.first;
114  const std::string& path_path = filesystem::normalize_path(path_ent.second, true);
115 
116  text_box_base& path_w = find_widget<text_box_base>(&window, path_wid_stem_ + path_id, false);
117  button& copy_w = find_widget<button>(&window, copy_wid_stem_ + path_id, false);
118  button& browse_w = find_widget<button>(&window, browse_wid_stem_ + path_id, false);
119 
120  path_w.set_value(path_path);
121  path_w.set_active(false);
122 
124  copy_w,
125  std::bind(&game_version::copy_to_clipboard_callback, this, path_path));
127  browse_w,
128  std::bind(&game_version::browse_directory_callback, this, path_path));
129 
131  // No point in displaying these on platforms that can't do
132  // open_object().
134  }
135 
137  copy_w.set_active(false);
138  copy_w.set_tooltip(_("Clipboard support not found, contact your packager"));
139  }
140  }
141 
142  button& stderr_button = find_widget<button>(&window, "open_stderr", false);
144  stderr_button.set_active(!log_path_.empty());
145 
146  //
147  // Build info tab.
148  //
149 
150  widget_data list_data;
151 
152  listbox& deps_listbox
153  = find_widget<listbox>(&window, "deps_listbox", false);
154 
155  for(const auto & dep : deps_)
156  {
157  list_data["dep_name"]["label"] = dep[0];
158 
159  list_data["dep_build_version"]["label"] = dep[1];
160 
161  // The build version is always known, but runtime version isn't, esp.
162  // for header-only libraries like Boost for which the concept does not
163  // apply.
164  if(!dep[2].empty()) {
165  list_data["dep_rt_version"]["label"] = dep[2];
166  } else {
167  list_data["dep_rt_version"]["label"] = font::unicode_em_dash;
168  }
169 
170  deps_listbox.add_row(list_data);
171  }
172 
173  deps_listbox.select_row(0);
174  list_data.clear();
175 
176  //
177  // Features tab.
178  //
179 
180  listbox& opts_listbox
181  = find_widget<listbox>(&window, "opts_listbox", false);
182 
183  for(const auto & opt : opts_)
184  {
185  list_data["opt_name"]["label"] = opt.name;
186 
187  if(opt.enabled) {
188  list_data["opt_status"]["label"] = text_feature_on;
189  } else {
190  list_data["opt_status"]["label"] = text_feature_off;
191  }
192  list_data["opt_status"]["use_markup"] = "true";
193 
194  opts_listbox.add_row(list_data);
195  }
196 
197  opts_listbox.select_row(0);
198  list_data.clear();
199 
200  //
201  // Set-up page stack and auxiliary controls last.
202  //
203 
204  stacked_widget& pager
205  = find_widget<stacked_widget>(&window, "tabs_container", false);
206  pager.select_layer(0);
207 
208  listbox& tab_bar
209  = find_widget<listbox>(&window, "tab_bar", false);
210 
211  window.keyboard_capture(&tab_bar);
212 
213  const unsigned tab_count = tab_bar.get_item_count();
214  VALIDATE(tab_count == pager.get_layer_count(), "Tab bar and container size mismatch");
215 
217  std::bind(&game_version::tab_switch_callback, this));
218 }
219 
221 {
222  stacked_widget& pager
223  = find_widget<stacked_widget>(get_window(), "tabs_container", false);
224  listbox& tab_bar
225  = find_widget<listbox>(get_window(), "tab_bar", false);
226 
227  pager.select_layer(std::max<int>(0, tab_bar.get_selected_row()));
228 }
229 
231 {
233 }
234 
236 {
238 }
239 
241 {
243 }
244 
246 {
248 }
249 
250 } // namespace dialogs
Simple push button.
Definition: button.hpp:36
virtual void set_active(const bool active) override
See styled_widget::set_active.
Definition: button.cpp:63
Dialog displaying the various paths used by the game to locate resource and configuration files.
const std::string path_wid_stem_
The display function.
void tab_switch_callback()
Callback function called when switching tabs.
std::array< std::string, 4 > deplist_entry
void report_copy_callback()
Callback function for the dialog-wide copy-to-clipboard button.
virtual void pre_show(window &window) override
Actions to be taken before showing the window.
void copy_to_clipboard_callback(const std::string &path)
Callback function for copy-to-clipboard action buttons.
std::map< std::string, std::string > path_map_
const std::string log_path_
path to current log file
std::vector< deplist_entry > deps_
void browse_directory_callback(const std::string &path)
Callback function for browse-directory action buttons.
std::vector< game_config::optional_feature > opts_
Abstract base class for all modal dialogs.
window * get_window()
Returns a pointer to the dialog's window.
The listbox class.
Definition: listbox.hpp:43
grid & add_row(const widget_item &item, const int index=-1)
When an item in the list is selected by the user we need to update the state.
Definition: listbox.cpp:59
bool select_row(const unsigned row, const bool select=true)
Selects a row.
Definition: listbox.cpp:243
int get_selected_row() const
Returns the first selected row.
Definition: listbox.cpp:268
unsigned get_item_count() const
Returns the number of items in the listbox.
Definition: listbox.cpp:124
A stacked widget holds several widgets on top of each other.
unsigned int get_layer_count() const
Gets the total number of layers.
void select_layer(const int layer)
Selects and displays a particular layer.
Base class for all visible items.
void set_tooltip(const t_string &tooltip)
virtual void set_label(const t_string &text)
Abstract base class for text items.
virtual void set_value(const std::string &text)
The set_value is virtual for the password_box class.
virtual void set_active(const bool active) override
See styled_widget::set_active.
void set_visible(const visibility visible)
Definition: widget.cpp:470
@ invisible
The user set the widget invisible, that means:
base class of top level items, the only item which needs to store the final canvases to draw on.
Definition: window.hpp:63
void keyboard_capture(widget *widget)
Definition: window.cpp:1215
Platform identification and version information functions.
Declarations for File-IO.
#define VGETTEXT(msgid,...)
Handy wrappers around interpolate_variables_into_string and gettext.
static std::string _(const char *str)
Definition: gettext.hpp:93
This file contains the window object, this object is a top level container which has the event manage...
void copy_to_clipboard(const std::string &text, const bool)
Copies text to the clipboard.
Definition: clipboard.cpp:32
bool available()
Whether wesnoth was compiled with support for a clipboard.
Definition: clipboard.cpp:53
bool open_object([[maybe_unused]] const std::string &path_or_url)
Definition: open.cpp:46
constexpr bool open_object_is_supported()
Returns whether open_object() is supported/implemented for the current platform.
Definition: open.hpp:54
std::string os_version()
Returns a string with the running OS name and version information.
Definition: version.cpp:216
std::string get_cache_dir()
Definition: filesystem.cpp:880
std::string get_user_config_dir()
Definition: filesystem.cpp:841
std::string get_user_data_dir()
Definition: filesystem.cpp:870
std::string get_saves_dir()
std::string get_screenshot_dir()
std::string get_logs_dir()
Definition: filesystem.cpp:875
std::string get_addons_dir()
std::string normalize_path(const std::string &fpath, bool normalize_separators, bool resolve_dot_entries)
Returns the absolute path of a file.
const std::string unicode_em_dash
Definition: constants.cpp:44
Game configuration data as global variables.
Definition: build_info.cpp:60
const std::string & library_name(LIBRARY_ID lib)
Retrieve the user-visible name for the given library.
Definition: build_info.cpp:385
std::string path
Definition: filesystem.cpp:83
std::string full_build_report()
Produce a bug report-style info dump.
Definition: build_info.cpp:663
std::vector< optional_feature > optional_features_table(bool localize)
Retrieve the features table.
Definition: build_info.cpp:348
const std::string & library_runtime_version(LIBRARY_ID lib)
Retrieve the runtime version number of the given library.
Definition: build_info.cpp:376
const std::string & library_build_version(LIBRARY_ID lib)
Retrieve the build-time version number of the given library.
Definition: build_info.cpp:367
std::string build_arch()
Obtain the processor architecture for this build.
Definition: build_info.cpp:315
const std::string revision
REGISTER_DIALOG(editor_edit_unit)
void connect_signal_notify_modified(dispatcher &dispatcher, const signal_notification &signal)
Connects a signal handler for getting a notification upon modification.
Definition: dispatcher.cpp:203
void connect_signal_mouse_left_click(dispatcher &dispatcher, const signal &signal)
Connects a signal handler for a left mouse button click.
Definition: dispatcher.cpp:177
std::map< std::string, widget_item > widget_data
Definition: widget.hpp:34
Definition: pump.hpp:41
std::string get_log_file_path()
Definition: log.cpp:280
std::map< std::string, t_string > string_map
Desktop environment interaction functions.
#define VALIDATE(cond, message)
The macro to use for the validation of WML.
#define e