1 /*
2    Copyright (C) 2017-2018 by the Battle for Wesnoth Project https://www.wesnoth.org/
3 
4    This program is free software; you can redistribute it and/or modify
5    it under the terms of the GNU General Public License as published by
6    the Free Software Foundation; either version 2 of the License, or
7    (at your option) any later version.
8    This program is distributed in the hope that it will be useful,
9    but WITHOUT ANY WARRANTY.
10 
11    See the COPYING file for more details.
12 */
13 
14 #define GETTEXT_DOMAIN "wesnoth-lib"
15 
16 #include "gui/dialogs/label_settings.hpp"
17 
18 #include "display.hpp"
19 #include "font/text_formatting.hpp"
20 #include "formatter.hpp"
21 #include "formula/string_utils.hpp"
22 #include "gettext.hpp"
23 #include "gui/auxiliary/find_widget.hpp"
24 #include "gui/widgets/label.hpp"
25 #include "gui/widgets/listbox.hpp"
26 #include "gui/widgets/settings.hpp"
27 #include "gui/widgets/styled_widget.hpp"
28 #include "gui/widgets/toggle_button.hpp"
29 #include "gui/widgets/window.hpp"
30 #include "map/label.hpp"
31 #include "team.hpp"
32 
33 #include <vector>
34 
35 namespace gui2
36 {
37 namespace dialogs
38 {
REGISTER_DIALOG(label_settings)39 REGISTER_DIALOG(label_settings)
40 
41 label_settings::label_settings(display_context& dc)
42 	: viewer_(dc)
43 {
44 	const std::vector<std::string>& all_categories = display::get_singleton()->labels().all_categories();
45 	const std::vector<std::string>& hidden_categories = viewer_.hidden_label_categories();
46 
47 	for(const std::string& cat : all_categories) {
48 		all_labels_[cat] = true;
49 
50 		// TODO: Translatable names for categories?
51 		if(cat.substr(0, 4) == "cat:") {
52 			labels_display_[cat] = cat.substr(4);
53 		} else if(cat == "team") {
54 			labels_display_[cat] = _("Team Labels");
55 		}
56 	}
57 
58 	for(const std::string& hidden_cat : hidden_categories) {
59 		all_labels_[hidden_cat] = false;
60 	}
61 
62 	for(std::size_t i = 0; i < viewer_.teams().size(); i++) {
63 		const team& team = viewer_.teams()[i];
64 		const std::string label_cat_key = "side:" + std::to_string(i + 1);
65 
66 		if(team.hidden()) {
67 			labels_display_[label_cat_key] = "";
68 			continue;
69 
70 		}
71 
72 		std::string team_name = team.side_name();
73 		if(team_name.empty()) {
74 			team_name = team.user_team_name();
75 		}
76 
77 		if(team_name.empty()) {
78 			team_name = _("Unknown");
79 		}
80 
81 		string_map subst;
82 		subst["side_number"] = std::to_string(i + 1);
83 		subst["name"] = team_name;
84 		labels_display_[label_cat_key] = VGETTEXT("Side $side_number ($name)", subst);
85 	}
86 }
87 
pre_show(window & window)88 void label_settings::pre_show(window& window)
89 {
90 	listbox& cats_listbox = find_widget<listbox>(&window, "label_types", false);
91 	std::map<std::string, string_map> list_data;
92 
93 	for(const auto& label_entry : all_labels_) {
94 		const std::string& category = label_entry.first;
95 		const bool visible = label_entry.second;
96 
97 		std::string name = labels_display_[category];
98 		if(category.substr(0, 5) == "side:") {
99 			// This means it's a hidden side, so don't show it.
100 			if(name.empty()) {
101 				continue;
102 			}
103 
104 			const int team = std::stoi(category.substr(5)) - 1;
105 			const color_t tc = game_config::tc_info(viewer_.teams()[team].color())[0];
106 
107 			name = (formatter() << font::span_color(tc) << name << "</span>").str();
108 		}
109 
110 		list_data["cat_name"]["label"] = name;
111 		grid* grid = &cats_listbox.add_row(list_data);
112 
113 		toggle_button& status = find_widget<toggle_button>(grid, "cat_status", false);
114 		status.set_value(visible);
115 
116 		connect_signal_notify_modified(status, std::bind(&label_settings::toggle_category, this, _1, category));
117 
118 		if(category.substr(0, 5) == "side:") {
119 			label& cat_name = find_widget<label>(grid, "cat_name", false);
120 			cat_name.set_use_markup(true);
121 		}
122 	}
123 }
124 
post_show(window &)125 void label_settings::post_show(window& /*window*/)
126 {
127 	if(get_retval() == retval::OK) {
128 		std::vector<std::string> hidden_categories;
129 
130 		for(const auto& lbl : all_labels_) {
131 			if(lbl.second == false) {
132 				hidden_categories.push_back(lbl.first);
133 			}
134 		}
135 
136 		viewer_.hidden_label_categories().swap(hidden_categories);
137 	}
138 }
139 
toggle_category(widget & box,const std::string & category)140 void label_settings::toggle_category(widget& box, const std::string& category)
141 {
142 	all_labels_[category] = static_cast<toggle_button&>(box).get_value_bool();
143 }
144 
145 } // namespace dialogs
146 } // namespace gui2
147