1 /*
2 Solar Conquest
3 Copyright (C) 2006 Greg Beaman
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
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18 */
19
20 #define MAP_SIZE 1000
21 #define TILE_SIZE 10
22
23 //Node for object list
24 class CObjectListNode
25 {
26 public:
27 void* obj;
28 CObjectListNode* prevNode;
29 CObjectListNode* nextNode;
30
31 CObjectListNode(void* store);
32 ~CObjectListNode();
33 };
34
CObjectListNode(void * store)35 CObjectListNode::CObjectListNode(void* store) { obj = store; prevNode = NULL; nextNode = NULL; }
~CObjectListNode()36 CObjectListNode::~CObjectListNode() {}
37
38 //Class to hold a list of objects
39 class CObjectList
40 {
41 public:
42 CObjectListNode* firstNode;
43
44 CObjectList();
45 ~CObjectList();
46
47 CObjectListNode* AddNode(void* obj);
48 CObjectListNode* GetNode(void* obj);
49 void DeleteNode(CObjectListNode* node);
50 void ClearAll();
51 };
52
CObjectList()53 CObjectList::CObjectList() { firstNode = NULL; }
~CObjectList()54 CObjectList::~CObjectList() { ClearAll(); }
55
AddNode(void * obj)56 CObjectListNode* CObjectList::AddNode(void* obj)
57 {
58 if (obj == NULL)
59 return NULL;
60
61 CObjectListNode* newNode;
62 newNode = new CObjectListNode(obj);
63 if (!newNode)
64 return NULL;
65 newNode->nextNode = firstNode;
66 if (firstNode)
67 firstNode->prevNode = newNode;
68 firstNode = newNode;
69 return newNode;
70 }
71
GetNode(void * obj)72 CObjectListNode* CObjectList::GetNode(void* obj)
73 {
74 CObjectListNode* cNode = firstNode;
75 while (cNode)
76 {
77 if (cNode->obj == obj)
78 return cNode;
79 cNode = cNode->nextNode;
80 }
81 return NULL;
82 }
83
DeleteNode(CObjectListNode * node)84 void CObjectList::DeleteNode(CObjectListNode* node)
85 {
86 if (!node)
87 return;
88
89 if (node->prevNode)
90 node->prevNode->nextNode = node->nextNode;
91 else
92 firstNode = node->nextNode;
93 if (node->nextNode)
94 node->nextNode->prevNode = node->prevNode;
95 delete node;
96 }
97
ClearAll()98 void CObjectList::ClearAll()
99 {
100 CObjectListNode* cNode = firstNode;
101 CObjectListNode* tNode;
102 while (cNode)
103 {
104 tNode = cNode->nextNode;
105 delete cNode;
106 cNode = tNode;
107 }
108 firstNode = NULL;
109 }
110
111 //Data for tile
112 struct TileData
113 {
114 CObjectList* list;
115 };
116
117 class CMap
118 {
119 protected:
120 TileData Tiles[MAP_SIZE][MAP_SIZE];
121
122 public:
123 CMap();
124 ~CMap();
125
126 bool ValidTile(int x, int y);
127
128 void ResetMap();
129
130 void AddObject(float x, float y, int radius, void* obj);
131 void DeleteObject(float x, float y, int radius, void* obj);
132
133 CObjectList* GetObjectList(int x, int y);
134 CObjectList* GetObjectList(float x, float y);
135 };
136
CMap()137 CMap::CMap()
138 {
139 for (int x=0; x < MAP_SIZE; x++)
140 for (int y=0; y < MAP_SIZE; y++)
141 {
142 Tiles[x][y].list = new CObjectList();
143 if (!Tiles[x][y].list)
144 DebugMessage(1,"Could not create object list for tile");
145 }
146 }
147
~CMap()148 CMap::~CMap()
149 {
150 for (int x=0; x < MAP_SIZE; x++)
151 for (int y=0; y < MAP_SIZE; y++)
152 {
153 delete Tiles[x][y].list;
154 Tiles[x][y].list = NULL;
155 }
156 }
157
ResetMap()158 void CMap::ResetMap()
159 {
160 for (int x=0; x < MAP_SIZE; x++)
161 for (int y=0; y < MAP_SIZE; y++)
162 if (Tiles[x][y].list)
163 Tiles[x][y].list->ClearAll();
164 }
165
ValidTile(int x,int y)166 bool CMap::ValidTile(int x, int y)
167 {
168 if (x < 0 || x >= MAP_SIZE)
169 return false;
170 if (y < 0 || y >= MAP_SIZE)
171 return false;
172 return true;
173 }
174
AddObject(float x,float y,int radius,void * obj)175 void CMap::AddObject(float x, float y, int radius, void* obj)
176 {
177 int sx,sy;
178 sx = (int)(x / TILE_SIZE);
179 sy = (int)(y / TILE_SIZE);
180
181 for (int tx = sx-radius; tx <= sx+radius; tx++)
182 {
183 for (int ty = sy-radius; ty <= sy+radius; ty++)
184 {
185 if (ValidTile(tx,ty))
186 if (Tiles[tx][ty].list)
187 Tiles[tx][ty].list->AddNode(obj);
188 }
189 }
190 }
191
DeleteObject(float x,float y,int radius,void * obj)192 void CMap::DeleteObject(float x, float y, int radius, void* obj)
193 {
194 int sx,sy;
195 sx = (int)(x / TILE_SIZE);
196 sy = (int)(y / TILE_SIZE);
197
198 for (int tx = sx-radius; tx <= sx+radius; tx++)
199 {
200 for (int ty = sy-radius; ty <= sy+radius; ty++)
201 {
202 if (ValidTile(tx,ty))
203 if (Tiles[tx][ty].list)
204 Tiles[tx][ty].list->DeleteNode(Tiles[tx][ty].list->GetNode(obj));
205 }
206 }
207 }
208
GetObjectList(int x,int y)209 CObjectList* CMap::GetObjectList(int x, int y)
210 {
211 if (ValidTile(x,y))
212 return Tiles[x][y].list;
213 return NULL;
214 }
215
GetObjectList(float x,float y)216 CObjectList* CMap::GetObjectList(float x, float y)
217 {
218 int sx,sy;
219 sx = (int)(x / TILE_SIZE);
220 sy = (int)(y / TILE_SIZE);
221
222 if (ValidTile(sx,sy))
223 return Tiles[sx][sy].list;
224 return NULL;
225 }
226
227 CMap* g_Map = NULL;
228