The Battle for Wesnoth  1.19.7+dev
undo_recruit_action.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2017 - 2024
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"
21 #include "units/map.hpp"
22 #include "units/unit.hpp"
23 #include "units/types.hpp"
24 #include "statistics.hpp"
25 #include "log.hpp"
26 #include "game_display.hpp"
27 
28 static lg::log_domain log_engine("engine");
29 #define ERR_NG LOG_STREAM(err, log_engine)
30 #define LOG_NG LOG_STREAM(info, log_engine)
31 
32 namespace actions::undo
33 {
35  const map_location& from)
36  : undo_action()
37  , shroud_clearing_action(recruited, loc)
38  , u_type(recruited->type())
39  , recruit_from(from)
40 {}
41 
42 static const unit_type& get_unit_type(const config& cfg)
43 {
44  const config& child = cfg.mandatory_child("unit");
45  const unit_type* u_type = unit_types.find(child["type"]);
46 
47  if(!u_type) {
48  // Bad data.
49  throw config::error("Invalid recruit; unit type '" + child["type"].str() + "' was not found.\n");
50  }
51  return *u_type;
52 }
54  : undo_action()
56  , u_type(get_unit_type(cfg))
57  , recruit_from(map_location(cfg.child_or_empty("leader"), nullptr))
58 {
59 }
60 
61 /**
62  * Writes this into the provided config.
63  */
64 void recruit_action::write(config & cfg) const
65 {
66  undo_action::write(cfg);
68 
69  recruit_from.write(cfg.add_child("leader"));
70  config & child = cfg.mandatory_child("unit");
71  child["type"] = u_type.parent_id();
72 }
73 
74 /**
75  * Undoes this action.
76  * @return true on success; false on an error.
77  */
78 bool recruit_action::undo(int side)
79 {
81  unit_map & units = resources::gameboard->units();
82  team &current_team = resources::gameboard->get_team(side);
83 
84  const map_location & recruit_loc = route.front();
85  unit_map::iterator un_it = units.find(recruit_loc);
86  if ( un_it == units.end() ) {
87  return false;
88  }
89 
90  const unit &un = *un_it;
92  current_team.spend_gold(-un.type().cost());
93 
94  //MP_COUNTDOWN take away recruit bonus
95  current_team.set_action_bonus_count(current_team.action_bonus_count() - 1);
96 
97  // invalidate before erasing allow us
98  // to also do the overlapped hexes
99  gui.invalidate(recruit_loc);
100  units.erase(recruit_loc);
101  return true;
102 }
104 
105 }
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:172
config & mandatory_child(config_key_type key, int n=0)
Returns the nth child with the given key, or throws an error if there is none.
Definition: config.cpp:366
config & add_child(config_key_type key)
Definition: config.cpp:440
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 un_recruit_unit(const unit &u)
Definition: statistics.cpp:194
This class stores all the data for a single 'side' (in game nomenclature).
Definition: team.hpp:75
void set_action_bonus_count(const int count)
Definition: team.hpp:200
int action_bonus_count() const
Definition: team.hpp:199
void spend_gold(const int amount)
Definition: team.hpp:195
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 unit_type * find(const std::string &key, unit_type::BUILD_STATUS status=unit_type::FULL) const
Finds a unit_type by its id() and makes sure it is built to the specified level.
Definition: types.cpp:1265
A single unit type that the player may recruit.
Definition: types.hpp:43
const std::string & parent_id() const
The id of the original type from which this (variation) descended.
Definition: types.hpp:145
int cost() const
Definition: types.hpp:172
This class represents a single unit of a specific type.
Definition: unit.hpp:133
const unit_type & type() const
This unit's type, accounting for gender and variation.
Definition: unit.hpp:355
Standard logging facilities (interface).
static const unit_type & get_unit_type(const config &cfg)
static auto reg_undo_recruit
General purpose widgets.
game_board * gameboard
Definition: resources.cpp:20
play_controller * controller
Definition: resources.cpp:21
std::shared_ptr< const unit > unit_const_ptr
Definition: ptr.hpp:27
base class for classes that clear srhoud (move/recruit/recall)
route_t route
The hexes occupied by the affected unit during this action.
recruit_action(const unit_const_ptr &recruited, const map_location &loc, const map_location &from)
virtual void write(config &cfg) const
Writes this into the provided config.
virtual bool undo(int side)
Undoes this action.
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:45
void write(config &cfg) const
Definition: location.cpp:225
unit_type_data unit_types
Definition: types.cpp:1500
static lg::log_domain log_engine("engine")