The Battle for Wesnoth  1.19.23+dev
undo_recall_action.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2017 - 2025
3  Part of the Battle for Wesnoth Project https://www.wesnoth.org/
4 
5  This program is free software; you can redistribute it and/or modify
6  it under the terms of the GNU General Public License as published by
7  the Free Software Foundation; either version 2 of the License, or
8  (at your option) any later version.
9  This program is distributed in the hope that it will be useful,
10  but WITHOUT ANY WARRANTY.
11 
12  See the COPYING file for more details.
13 */
14 
16 
17 #include "game_board.hpp"
18 #include "play_controller.hpp"
19 #include "resources.hpp"
20 #include "team.hpp"
22 #include "units/map.hpp"
23 #include "units/unit.hpp"
24 #include "statistics.hpp"
25 #include "log.hpp"
26 #include "game_display.hpp"
27 #include "whiteboard/manager.hpp"
28 
29 static lg::log_domain log_engine("engine");
30 #define ERR_NG LOG_STREAM(err, log_engine)
31 #define LOG_NG LOG_STREAM(info, log_engine)
32 
33 namespace actions::undo
34 {
36  const map_location& from)
37  : undo_action()
38  , shroud_clearing_action(recalled, loc)
39  , id(recalled->id())
40  , prev_mp(recalled->movement_left(true))
41  , prev_ap(recalled->attacks_left(true))
42  , recall_from(from)
43 {}
44 
46  : undo_action()
48  , id(cfg["id"])
49  , prev_mp(cfg["previous_movement"].to_int())
50  , prev_ap(cfg["previous_attacks"].to_int())
51  , recall_from(map_location(cfg.child_or_empty("leader"), nullptr))
52 {}
53 
54 /**
55  * Writes this into the provided config.
56  */
58 {
61 
62  recall_from.write(cfg.add_child("leader"));
63  cfg["id"] = id;
64  cfg["previous_movement"] = prev_mp;
65  cfg["previous_attacks"] = prev_ap;
66 }
67 
68 /**
69  * Undoes this action.
70  * @return true on success; false on an error.
71  */
72 bool recall_action::undo(int side)
73 {
75  unit_map & units = resources::gameboard->units();
76  team &current_team = resources::gameboard->get_team(side);
77 
78  const map_location & recall_loc = route.front();
79  unit_map::iterator un_it = units.find(recall_loc);
80  if ( un_it == units.end() ) {
81  return false;
82  }
83 
84  unit_ptr un = un_it.get_shared_ptr();
85  if (!un) {
86  return false;
87  }
88 
90  int cost = un->recall_cost();
91  if (cost < 0) {
92  current_team.spend_gold(-current_team.recall_cost());
93  }
94  else {
95  current_team.spend_gold(-cost);
96  }
97 
98  un->set_attacks(prev_ap);
99  un->set_movement(prev_mp);
100  current_team.recall_list().add(un);
101  // Invalidate everything, not just recall_loc, in case the sprite
102  // extends into adjacent hexes (Horseman) or even farther away (Fire
103  // Dragon)
104  gui.invalidate_all();
105  units.erase(recall_loc);
106  resources::whiteboard->on_kill_unit();
107  un->anim_comp().clear_haloes();
108  return true;
109 }
111 
112 }
map_location loc
Definition: move.cpp:172
A config object defines a single node in a WML file, with access to child nodes.
Definition: config.hpp:157
config & add_child(std::string_view key)
Definition: config.cpp:436
team & get_team(int i)
Definition: game_board.hpp:92
virtual const unit_map & units() const override
Definition: game_board.hpp:107
static game_display * get_singleton()
statistics_t & statistics()
void add(const unit_ptr &ptr, int pos=-1)
Add a unit to the list.
void un_recall_unit(const unit &u)
Definition: statistics.cpp:187
This class stores all the data for a single 'side' (in game nomenclature).
Definition: team.hpp:74
int recall_cost() const
Definition: team.hpp:195
void spend_gold(const int amount)
Definition: team.hpp:218
recall_list_manager & recall_list()
Definition: team.hpp:239
Container associating units to locations.
Definition: map.hpp:98
unit_iterator end()
Definition: map.hpp:428
unit_iterator find(std::size_t id)
Definition: map.cpp:302
std::size_t erase(const map_location &l)
Erases the unit at location l, if any.
Definition: map.cpp:289
const config * cfg
std::string id
Text to match against addon_info.tags()
Definition: manager.cpp:199
Standard logging facilities (interface).
static auto reg_undo_recall
General purpose widgets.
game_board * gameboard
Definition: resources.cpp:20
play_controller * controller
Definition: resources.cpp:21
std::shared_ptr< wb::manager > whiteboard
Definition: resources.cpp:33
std::shared_ptr< const unit > unit_const_ptr
Definition: ptr.hpp:27
std::shared_ptr< unit > unit_ptr
Definition: ptr.hpp:26
base class for classes that clear srhoud (move/recruit/recall)
route_t route
The hexes occupied by the affected unit during this action.
virtual bool undo(int side)
Undoes this action.
recall_action(const unit_const_ptr &recalled, const map_location &loc, const map_location &from)
virtual void write(config &cfg) const
Writes this into the provided config.
Records information to be able to undo an action.
Definition: undo_action.hpp:80
virtual void write(config &cfg) const
Writes this into the provided config.
Definition: undo_action.hpp:91
Encapsulates the map of the game.
Definition: location.hpp:46
void write(config &cfg) const
Definition: location.cpp:223
pointer get_shared_ptr() const
This is exactly the same as operator-> but it's slightly more readable, and can replace &*iter syntax...
Definition: map.hpp:217
static lg::log_domain log_engine("engine")