The Battle for Wesnoth  1.15.3+dev
display_context.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2014 - 2018 by Chris Beck <render787@gmail.com>
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 
15 #include "display_context.hpp"
16 
17 #include "map/map.hpp"
18 #include "map/location.hpp"
19 #include "team.hpp"
20 #include "units/unit.hpp"
21 #include "units/map.hpp"
22 
23 const team& display_context::get_team(int side) const
24 {
25  return teams().at(side - 1);
26 }
27 
28 bool display_context::would_be_discovered(const map_location & loc, int side_num, bool see_all)
29 {
31  get_adjacent_tiles(loc,adjs.data());
32 
33  for (const map_location &u_loc : adjs)
34  {
35  unit_map::const_iterator u_it = units().find(u_loc);
36  if (!u_it.valid()) {
37  continue;
38  }
39  const unit & u = *u_it;
40  if (get_team(side_num).is_enemy(u.side()) && !u.incapacitated()) {
41  // Enemy spotted in adjacent tiles, check if we can see him.
42  // Watch out to call invisible with see_all=true to avoid infinite recursive calls!
43  if(see_all) {
44  return true;
45  } else if (!get_team(side_num).fogged(u_loc)
46  && !u.invisible(u_loc, true)) {
47  return true;
48  }
49  }
50  }
51  return false;
52 }
53 
54 const unit * display_context::get_visible_unit(const map_location & loc, const team &current_team, bool see_all) const
55 {
56  if (!map().on_board(loc)) return nullptr;
57  const unit_map::const_iterator u = units().find(loc);
58  if (!u.valid() || !u->is_visible_to_team(current_team, see_all)) {
59  return nullptr;
60  }
61  return &*u;
62 }
63 
64 unit_const_ptr display_context::get_visible_unit_shared_ptr(const map_location & loc, const team &current_team, bool see_all) const
65 {
66  if (!map().on_board(loc)) return nullptr;
67  const unit_map::const_iterator u = units().find(loc);
68  if (!u.valid() || !u->is_visible_to_team(current_team, see_all)) {
69  return unit_const_ptr();
70  }
71  return u.get_shared_ptr();
72 }
73 
74 /**
75  * Will return true iff the unit @a u has any possible moves
76  * it can do (including attacking etc).
77  */
78 
80 {
81  if(!u.attacks_left() && u.movement_left()==0)
82  return false;
83 
84  // Units with goto commands that have already done their gotos this turn
85  // (i.e. don't have full movement left) should have red globes.
86  if(u.has_moved() && u.has_goto()) {
87  return false;
88  }
89 
90  const team &current_team = get_team(u.side());
91 
93  get_adjacent_tiles(u.get_location(), locs.data());
94  for(unsigned n = 0; n < locs.size(); ++n) {
95  if (map().on_board(locs[n])) {
96  const unit_map::const_iterator i = units().find(locs[n]);
97  if (i.valid() && !i->incapacitated() &&
98  current_team.is_enemy(i->side())) {
99  return true;
100  }
101 
102  if (u.movement_cost(map()[locs[n]]) <= u.movement_left()) {
103  return true;
104  }
105  }
106  }
107 
108  return false;
109 }
110 
111 
112 /**
113  * Given the location of a village, will return the 0-based index
114  * of the team that currently owns it, and -1 if it is unowned.
115  */
117 {
118  const std::vector<team> & t = teams();
119  for(std::size_t i = 0; i != t.size(); ++i) {
120  if(t[i].owns_village(loc))
121  return i + 1;
122  }
123  return 0;
124 }
125 
126 /**
127  * Determine if we are an observer, by checking if every team is not locally controlled
128  */
130 {
131  for (const team &t : teams()) {
132  if (t.is_local())
133  return false;
134  }
135 
136  return true;
137 }
138 
139 /// Static info getters previously declared at global scope in unit.?pp
140 
141 int display_context::side_units(int side) const
142 {
143  int res = 0;
144  for (const unit &u : units()) {
145  if (u.side() == side) ++res;
146  }
147  return res;
148 }
149 
151 {
152  int res = 0;
153  for (const unit &u : units()) {
154  if (u.side() == side) res += u.cost();
155  }
156  return res;
157 }
158 
159 int display_context::side_upkeep(int side) const
160 {
161  int res = 0;
162  for (const unit &u : units()) {
163  if (u.side() == side) res += u.upkeep();
164  }
165  return res;
166 }
167 
169  : side(tm.side())
170  , units(dc.side_units(side))
171  , upkeep(dc.side_upkeep(side))
172  , expenses(std::max<int>(0, upkeep - tm.support()))
173  , net_income(tm.total_income() - expenses)
174 {
175 }
int village_owner(const map_location &loc) const
Given the location of a village, will return the 1-based number of the team that currently owns it...
int attacks_left() const
Gets the remaining number of attacks this unit can perform this turn.
Definition: unit.hpp:992
const team & get_team(int side) const
void get_adjacent_tiles(const map_location &a, map_location *res)
Function which, given a location, will place all adjacent locations in res.
Definition: location.cpp:474
This class represents a single unit of a specific type.
Definition: unit.hpp:129
int movement_cost(const t_translation::terrain_code &terrain) const
Get the unit&#39;s movement cost on a particular terrain.
Definition: unit.hpp:1426
const unit * get_visible_unit(const map_location &loc, const team &current_team, bool see_all=false) const
STL namespace.
bool on_board(const map_location &loc) const
Tell if a location is on the map.
Definition: map.cpp:377
-file sdl_utils.hpp
bool unit_can_move(const unit &u) const
Will return true iff the unit u has any possible moves it can do (including attacking etc)...
virtual const gamemap & map() const =0
team_data(const display_context &dc, const team &tm)
std::shared_ptr< const unit > unit_const_ptr
Definition: ptr.hpp:29
This class stores all the data for a single &#39;side&#39; (in game nomenclature).
Definition: team.hpp:44
int side_upkeep(int side_num) const
bool is_enemy(int n) const
Definition: team.hpp:243
virtual const unit_map & units() const =0
std::array< map_location, 6 > adjacent_loc_array_t
Definition: location.hpp:170
Encapsulates the map of the game.
Definition: location.hpp:42
int side_units_cost(int side_num) const
Returns the total cost of units of side side_num.
unit_iterator find(std::size_t id)
Definition: map.cpp:311
bool invisible(const map_location &loc, bool see_all=true) const
Definition: unit.cpp:2431
bool has_moved() const
Checks if this unit has moved.
Definition: unit.hpp:1298
pointer get_shared_ptr() const
This is exactly the same as operator-> but it&#39;s slightly more readable, and can replace &*iter syntax...
Definition: map.hpp:220
std::size_t i
Definition: function.cpp:933
virtual const std::vector< team > & teams() const =0
bool is_observer() const
Check if we are an observer in this game.
bool has_goto() const
Gets whether this unit has a multi-turn destination set.
Definition: unit.hpp:1368
unit_const_ptr get_visible_unit_shared_ptr(const map_location &loc, const team &current_team, bool see_all=false) const
double t
Definition: astarsearch.cpp:64
const map_location & get_location() const
The current map location this unit is at.
Definition: unit.hpp:1343
bool incapacitated() const
Check if the unit has been petrified.
Definition: unit.hpp:904
bool fogged(const map_location &loc) const
Definition: team.cpp:662
int side() const
The side this unit belongs to.
Definition: unit.hpp:341
int side_units(int side_num) const
Returns the number of units of the side side_num.
bool valid() const
Definition: map.hpp:276
static map_location::DIRECTION n
bool would_be_discovered(const map_location &loc, int side_num, bool see_all=true)
Given a location and a side number, indicates whether an invisible unit of that side at that location...
int movement_left() const
Gets how far a unit can move, considering the incapacitated flag.
Definition: unit.hpp:1268