1 // Copyright (C) 2001, 2003 Michael Bartl
2 // Copyright (C) 2004 Ulf Lorenz
3 // Copyright (C) 2005, 2006 Andrea Paternesi
4 // Copyright (C) 2007, 2008, 2009 Ben Asselstine
5 // Copyright (C) 2008 Ole Laursen
7 // This program is free software; you can redistribute it and/or modify
8 // it under the terms of the GNU General Public License as published by
9 // the Free Software Foundation; either version 3 of the License, or
10 // (at your option) any later version.
12 // This program is distributed in the hope that it will be useful,
13 // but WITHOUT ANY WARRANTY; without even the implied warranty of
14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 // GNU Library General Public License for more details.
17 // You should have received a copy of the GNU General Public License
18 // along with this program; if not, write to the Free Software
19 // Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
22 #ifndef LOCATIONLIST_H
23 #define LOCATIONLIST_H
29 #include "PathCalculator.h"
33 /** A list for object instances
35 * This class extends the stl lists by adding the functions getObjectAt()
36 * which return the object at position (x,y). Necessary for such things as
42 template<class T> class LocationList : public std::list<T>
49 for (typename LocationList<T>::iterator it = this->begin(); it != this->end(); ++it)
59 int size = t->getSize();
60 for (int i = 0; i < size; i++)
61 for (int j = 0; j < size; j++)
63 Vector<int> pos = t->getPos() + Vector<int>(i,j);
69 this->erase(std::find(this->begin(), this->end(), t));
70 d_id.erase(d_id.find(t->getId()));
71 int size = t->getSize();
72 for (int i = 0; i < size; i++)
73 for (int j = 0; j < size; j++)
75 Vector<int> pos = t->getPos() + Vector<int>(i,j);
76 d_object.erase(d_object.find(pos));
81 //! Returns the object at position (x,y).
82 T getObjectAt(int x, int y) const
84 Vector<int> pos = Vector<int>(x,y);
86 if (d_object.find(pos) == d_object.end())
89 return (*d_object.find(pos)).second;
92 //! Returns the object at position pos.
93 T getObjectAt(const Vector<int>& pos) const
95 return getObjectAt(pos.x, pos.y);
98 T getNearestObjectInDir(const Vector<int> &pos, const Vector<int> dir) const
101 typename LocationList<T>::const_iterator diffit;
102 for (typename LocationList<T>::const_iterator it = this->begin(); it != this->end(); ++it)
104 Vector<int> p = (*it)->getPos();
105 int delta = abs(p.x - pos.x) + abs(p.y - pos.y);
106 //if dir is -1, then the difference between pos.x and p.x should be positive
107 //if dir is +1, then the difference between pos.x and p.x should be negative
108 //if looking west, and the object is to the east
109 if (dir.x < 0 && (pos.x - p.x) <= 0)
111 //if looking east , and the object is to the west
112 if (dir.x > 0 && (pos.x - p.x) >= 0)
114 //if looking north, and the object is to the south
115 if (dir.y < 0 && (pos.y - p.y) <= 0)
117 //if looking south, and the object is to the north
118 if (dir.y > 0 && (pos.y - p.y) >= 0)
121 if ((diff > delta) || (diff == -1))
127 if (diff == -1) return 0;
131 T getClosestObject (const Stack *stack, std::list<bool (*)(void*)> *filters) const
134 typename LocationList<T>::const_iterator diffit;
135 PathCalculator pc(stack, true, 0, 0);
136 for (typename LocationList<T>::const_iterator it = this->begin(); it != this->end(); ++it)
138 int delta = pc.calculate((*it)->getPos());
143 std::list<bool (*)(void*)>::iterator fit = filters->begin();
144 bool filtered = false;
145 for (; fit != filters->end(); fit++)
147 if ((*fit)(*it) == true)
158 if ((diff > delta) || (diff == -1))
164 if (diff == -1) return 0;
168 T getClosestObject (const Stack *stack) const
170 return getClosestObject (stack, NULL);
173 T getNearestObject (const Vector<int>& pos, std::list<bool (*)(void*)> *filters) const
176 typename LocationList<T>::const_iterator diffit;
177 for (typename LocationList<T>::const_iterator it = this->begin(); it != this->end(); ++it)
179 Vector<int> p = (*it)->getPos();
180 int delta = abs(p.x - pos.x) + abs(p.y - pos.y);
183 std::list<bool (*)(void*)>::iterator fit = filters->begin();
184 bool filtered = false;
185 for (; fit != filters->end(); fit++)
187 if ((*fit)(*it) == true)
198 if ((diff > delta) || (diff == -1))
204 if (diff == -1) return 0;
208 T getNearestObject (const Vector<int>& pos) const
210 return getNearestObject (pos, NULL);
213 T getNearestObjectBefore (const Vector<int>& pos, int dist) const
215 T t = getNearestObject(pos);
218 if (t->getPos().x <= pos.x + dist && t->getPos().x >= pos.x - dist &&
219 t->getPos().y <= pos.y + dist && t->getPos().y >= pos.y - dist)
224 T getNearestObjectAfter(const Vector<int>& pos, int dist,
225 std::list<bool (*)(void*)> *filters) const
228 typename LocationList<T>::const_iterator diffit;
230 for (typename LocationList<T>::const_iterator it = this->begin(); it != this->end(); ++it)
234 std::list<bool (*)(void*)>::iterator fit = filters->begin();
235 bool filtered = false;
236 for (; fit != filters->end(); fit++)
238 if ((*fit)(*it) == true)
249 Vector<int> p = (*it)->getPos();
250 int delta = abs(p.x - pos.x);
251 if (delta < abs(p.y - pos.y))
252 delta = abs(p.y - pos.y);
254 if ((diff > delta && delta >= dist) || (diff == -1))
261 if (diff == -1) return 0;
265 T getById(guint32 id)
267 if (d_id.find(id) == d_id.end())
270 return (*d_id.find(id)).second;
275 typedef std::map<Vector<int>, T> PositionMap;
276 typedef std::map<guint32, T> IdMap;
277 PositionMap d_object;
282 #endif // LOCATIONLIST_H