/* Copyright (C) 2016 - 2022 Part of the Battle for Wesnoth Project https://www.wesnoth.org/ This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY. See the COPYING file for more details. */ #define GETTEXT_DOMAIN "wesnoth-lib" #include "gui/dialogs/unit_recall.hpp" #include "font/text_formatting.hpp" #include "gui/auxiliary/find_widget.hpp" #include "gui/core/log.hpp" #include "gui/dialogs/edit_text.hpp" #include "gui/dialogs/message.hpp" #include "gui/widgets/listbox.hpp" #include "gui/widgets/settings.hpp" #include "gui/widgets/button.hpp" #include "gui/widgets/image.hpp" #include "gui/widgets/label.hpp" #include "gui/widgets/text_box.hpp" #include "gui/widgets/toggle_button.hpp" #include "gui/widgets/unit_preview_pane.hpp" #include "gui/widgets/window.hpp" #include "help/help.hpp" #include "game_board.hpp" #include "gettext.hpp" #include "replay_helper.hpp" #include "play_controller.hpp" #include "resources.hpp" #include "synced_context.hpp" #include "team.hpp" #include "units/types.hpp" #include "units/unit.hpp" #include "units/ptr.hpp" #include #include "whiteboard/manager.hpp" #include static lg::log_domain log_display("display"); #define LOG_DP LOG_STREAM(info, log_display) namespace gui2::dialogs { // Index 2 is by-level static listbox::order_pair sort_last {-1, sort_order::type::none}; static listbox::order_pair sort_default { 2, sort_order::type::descending}; REGISTER_DIALOG(unit_recall) unit_recall::unit_recall(std::vector& recall_list, team& team) : recall_list_(recall_list) , team_(team) , selected_index_() , filter_options_() , last_words_() { } template static void dump_recall_list_to_console(const T& units) { log_scope2(log_display, "dump_recall_list_to_console()") LOG_DP << "size: " << units.size(); std::size_t idx = 0; for(const auto& u_ptr : units) { LOG_DP << "\tunit[" << (idx++) << "]: " << u_ptr->id() << " name = '" << u_ptr->name() << "'"; } } static const color_t inactive_row_color(0x96, 0x96, 0x96); static const inline std::string maybe_inactive(const std::string& str, bool active) { if(active) return str; else return font::span_color(inactive_row_color, str); } static std::string format_level_string(const int level, bool recallable) { std::string lvl = std::to_string(level); if(!recallable) { // Same logic as when recallable, but always in inactive_row_color. if(level < 2) { return font::span_color(inactive_row_color, lvl); } else { return font::span_color(inactive_row_color, "" + lvl + ""); } } else if(level < 1) { return font::span_color(inactive_row_color, lvl); } else if(level == 1) { return lvl; } else if(level == 2) { return "" + lvl + ""; } else { return"" + lvl + ""; } } static std::string format_cost_string(int unit_recall_cost, const int team_recall_cost) { std::stringstream str; if(unit_recall_cost < 0) { unit_recall_cost = team_recall_cost; } if(unit_recall_cost > team_recall_cost) { str << "" << unit_recall_cost << ""; } else if(unit_recall_cost == team_recall_cost) { str << unit_recall_cost; } else if(unit_recall_cost < team_recall_cost) { str << "" << unit_recall_cost << ""; } return str.str(); } static std::string get_title_suffix(int side_num) { if(!resources::gameboard) { return ""; } unit_map& units = resources::gameboard->units(); int controlled_recruiters = 0; for(const auto& team : resources::gameboard->teams()) { if(team.is_local_human() && !team.recruits().empty() && units.find_leader(team.side()) !=units.end()) { ++controlled_recruiters; } } std::stringstream msg; if(controlled_recruiters >= 2) { unit_map::const_iterator leader = resources::gameboard->units().find_leader(side_num); if(leader != resources::gameboard->units().end() && !leader->name().empty()) { msg << " (" << leader->name(); msg << ")"; } } return msg.str(); } void unit_recall::pre_show(window& window) { label& title = find_widget