(svn r27770) -Fix [FS#6540]: Initialize variables in station_sl.cpp (JGR)
[openttd.git] / src / pathfinder / yapf / yapf_destrail.hpp
blob681034a2f527cd363712a727fb701ee6e779d6f6
1 /* $Id$ */
3 /*
4 * This file is part of OpenTTD.
5 * OpenTTD 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, version 2.
6 * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
7 * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see <http://www.gnu.org/licenses/>.
8 */
10 /** @file yapf_destrail.hpp Determining the destination for rail vehicles. */
12 #ifndef YAPF_DESTRAIL_HPP
13 #define YAPF_DESTRAIL_HPP
15 class CYapfDestinationRailBase {
16 protected:
17 RailTypes m_compatible_railtypes;
19 public:
20 void SetDestination(const Train *v, bool override_rail_type = false)
22 m_compatible_railtypes = v->compatible_railtypes;
23 if (override_rail_type) m_compatible_railtypes |= GetRailTypeInfo(v->railtype)->compatible_railtypes;
26 bool IsCompatibleRailType(RailType rt)
28 return HasBit(m_compatible_railtypes, rt);
31 RailTypes GetCompatibleRailTypes() const
33 return m_compatible_railtypes;
37 template <class Types>
38 class CYapfDestinationAnyDepotRailT : public CYapfDestinationRailBase {
39 public:
40 typedef typename Types::Tpf Tpf; ///< the pathfinder class (derived from THIS class)
41 typedef typename Types::NodeList::Titem Node; ///< this will be our node type
42 typedef typename Node::Key Key; ///< key to hash tables
44 /** to access inherited path finder */
45 Tpf& Yapf()
47 return *static_cast<Tpf *>(this);
50 /** Called by YAPF to detect if node ends in the desired destination */
51 inline bool PfDetectDestination(Node &n)
53 return PfDetectDestination(n.GetLastTile(), n.GetLastTrackdir());
56 /** Called by YAPF to detect if node ends in the desired destination */
57 inline bool PfDetectDestination(TileIndex tile, Trackdir td)
59 bool bDest = IsRailDepotTile(tile);
60 return bDest;
63 /**
64 * Called by YAPF to calculate cost estimate. Calculates distance to the destination
65 * adds it to the actual cost from origin and stores the sum to the Node::m_estimate
67 inline bool PfCalcEstimate(Node &n)
69 n.m_estimate = n.m_cost;
70 return true;
74 template <class Types>
75 class CYapfDestinationAnySafeTileRailT : public CYapfDestinationRailBase {
76 public:
77 typedef typename Types::Tpf Tpf; ///< the pathfinder class (derived from THIS class)
78 typedef typename Types::NodeList::Titem Node; ///< this will be our node type
79 typedef typename Node::Key Key; ///< key to hash tables
80 typedef typename Types::TrackFollower TrackFollower; ///< TrackFollower. Need to typedef for gcc 2.95
82 /** to access inherited path finder */
83 Tpf& Yapf()
85 return *static_cast<Tpf *>(this);
88 /** Called by YAPF to detect if node ends in the desired destination */
89 inline bool PfDetectDestination(Node &n)
91 return PfDetectDestination(n.GetLastTile(), n.GetLastTrackdir());
94 /** Called by YAPF to detect if node ends in the desired destination */
95 inline bool PfDetectDestination(TileIndex tile, Trackdir td)
97 return IsSafeWaitingPosition(Yapf().GetVehicle(), tile, td, true, !TrackFollower::Allow90degTurns()) &&
98 IsWaitingPositionFree(Yapf().GetVehicle(), tile, td, !TrackFollower::Allow90degTurns());
102 * Called by YAPF to calculate cost estimate. Calculates distance to the destination
103 * adds it to the actual cost from origin and stores the sum to the Node::m_estimate.
105 inline bool PfCalcEstimate(Node &n)
107 n.m_estimate = n.m_cost;
108 return true;
112 template <class Types>
113 class CYapfDestinationTileOrStationRailT : public CYapfDestinationRailBase {
114 public:
115 typedef typename Types::Tpf Tpf; ///< the pathfinder class (derived from THIS class)
116 typedef typename Types::NodeList::Titem Node; ///< this will be our node type
117 typedef typename Node::Key Key; ///< key to hash tables
119 protected:
120 TileIndex m_destTile;
121 TrackdirBits m_destTrackdirs;
122 StationID m_dest_station_id;
124 /** to access inherited path finder */
125 Tpf& Yapf()
127 return *static_cast<Tpf *>(this);
130 public:
131 void SetDestination(const Train *v)
133 switch (v->current_order.GetType()) {
134 case OT_GOTO_WAYPOINT:
135 if (!Waypoint::Get(v->current_order.GetDestination())->IsSingleTile()) {
136 /* In case of 'complex' waypoints we need to do a look
137 * ahead. This look ahead messes a bit about, which
138 * means that it 'corrupts' the cache. To prevent this
139 * we disable caching when we're looking for a complex
140 * waypoint. */
141 Yapf().DisableCache(true);
143 /* FALL THROUGH */
144 case OT_GOTO_STATION:
145 m_destTile = CalcClosestStationTile(v->current_order.GetDestination(), v->tile, v->current_order.IsType(OT_GOTO_STATION) ? STATION_RAIL : STATION_WAYPOINT);
146 m_dest_station_id = v->current_order.GetDestination();
147 m_destTrackdirs = INVALID_TRACKDIR_BIT;
148 break;
150 default:
151 m_destTile = v->dest_tile;
152 m_dest_station_id = INVALID_STATION;
153 m_destTrackdirs = TrackStatusToTrackdirBits(GetTileTrackStatus(v->dest_tile, TRANSPORT_RAIL, 0));
154 break;
156 CYapfDestinationRailBase::SetDestination(v);
159 /** Called by YAPF to detect if node ends in the desired destination */
160 inline bool PfDetectDestination(Node &n)
162 return PfDetectDestination(n.GetLastTile(), n.GetLastTrackdir());
165 /** Called by YAPF to detect if node ends in the desired destination */
166 inline bool PfDetectDestination(TileIndex tile, Trackdir td)
168 bool bDest;
169 if (m_dest_station_id != INVALID_STATION) {
170 bDest = HasStationTileRail(tile)
171 && (GetStationIndex(tile) == m_dest_station_id)
172 && (GetRailStationTrack(tile) == TrackdirToTrack(td));
173 } else {
174 bDest = (tile == m_destTile)
175 && ((m_destTrackdirs & TrackdirToTrackdirBits(td)) != TRACKDIR_BIT_NONE);
177 return bDest;
181 * Called by YAPF to calculate cost estimate. Calculates distance to the destination
182 * adds it to the actual cost from origin and stores the sum to the Node::m_estimate
184 inline bool PfCalcEstimate(Node &n)
186 static const int dg_dir_to_x_offs[] = {-1, 0, 1, 0};
187 static const int dg_dir_to_y_offs[] = {0, 1, 0, -1};
188 if (PfDetectDestination(n)) {
189 n.m_estimate = n.m_cost;
190 return true;
193 TileIndex tile = n.GetLastTile();
194 DiagDirection exitdir = TrackdirToExitdir(n.GetLastTrackdir());
195 int x1 = 2 * TileX(tile) + dg_dir_to_x_offs[(int)exitdir];
196 int y1 = 2 * TileY(tile) + dg_dir_to_y_offs[(int)exitdir];
197 int x2 = 2 * TileX(m_destTile);
198 int y2 = 2 * TileY(m_destTile);
199 int dx = abs(x1 - x2);
200 int dy = abs(y1 - y2);
201 int dmin = min(dx, dy);
202 int dxy = abs(dx - dy);
203 int d = dmin * YAPF_TILE_CORNER_LENGTH + (dxy - 1) * (YAPF_TILE_LENGTH / 2);
204 n.m_estimate = n.m_cost + d;
205 assert(n.m_estimate >= n.m_parent->m_estimate);
206 return true;
210 #endif /* YAPF_DESTRAIL_HPP */