1 //#define DisplayRegions
2 #define DisplayFinalRegions
5 using System.Collections.Generic;
8 using Microsoft.Xna.Framework;
13 /// AI infomation to be used by monsters. The map is split into deferent regions,
14 /// each region is then linked to other regions that it can see.
20 List<Region> regionList;
26 regions = new int[game.State.Map.Width, game.State.Map.Height];
27 regionList = new List<Region>();
30 //set all square to -1 to show they have not been assigned to a region yet.
31 for (int y = 0; y < regions.GetLength(1); y++)
33 for (int x = 0; x < regions.GetLength(0); x++)
38 regionList.Add(new Region(0)); //region 0 will represent all walls and things like it.
45 foreach (Region r in regionList)
49 #if (DisplayRegions || DisplayFinalRegions)
56 /// check to see if a spot on the map is visible from another spot
58 /// <param name="curX">Current X position</param>
59 /// <param name="curY">Current Y position</param>
60 /// <param name="testX">X location to test</param>
61 /// <param name="testY">Y location to test</param>
62 public bool spaceVisible(int curX, int curY, int testX, int testY)
64 return regionList[regions[curX, curY]].VisibleRegions.Contains(regions[testX, testY]);
66 public bool spaceVisible(Point Monster, Point Player )
68 return regionList[regions[Monster.X, Monster.Y]].VisibleRegions.Contains(regions[Player.X, Player.Y]);
70 //find regions in map. these regions will be large groups of connected grid squares.
71 public int setUpRegions()
74 //find open space that has not been assigned yet
75 for (int y = 0; y < regions.GetLength(1); y++)
77 for (int x = 0; x < regions.GetLength(0); x++)
79 if (regions[x, y] == -1 && spaceOpen(x, y))
82 regionList.Add(new Region(regionCnt));
85 else if (regions[x, y] == -1) //grid square is a wall
89 else //grid already assigned to region, do nothing
95 return regionList.Count;
98 #region Private Methods
99 private void createRegion(int x, int y)
101 regionList[regionCnt].Left = x;
102 regionList[regionCnt].Top = y;
104 for (int rY = 0; rY < 5 && y + rY < regions.GetLength(1); rY++) // creates a region as large as possible up to 5x5
106 for (int rX = 0; rX < 5 && x + rX < regions.GetLength(0); rX++)
108 if (regions[x + rX, y + rY] == -1 && spaceOpen(x + rX, y + rY))
110 regions[x + rX, y + rY] = regionCnt;
112 else if (regions[x + rX, y + rY] == -1) //grid square is a wall
114 regions[x + rX, y + rY] = 0;
115 regionList[regionCnt].Right = x + rX;
116 regionList[regionCnt].Bottom = y + rY;
120 if (!spaceOpen(x + rX + 1, y + rY)) // hit horizontal wall end region
121 if(x + rX >= regions.GetLength(0)-1)
128 //todo: figure out how to get region to stop being created when
130 else //grid already assigned to region, do nothing
133 regionList[regionCnt].Right = x + rX;
136 regionList[regionCnt].Bottom = y + rY;
143 private bool spaceOpen(int x, int y)
145 if (x >= regions.GetLength(0)) return false;
146 if (y >= regions.GetLength(1)) return false;
147 return !game.State.Map.IsWall(x, y);
149 //TODO: scans out from each corner, some areas are still missed
150 private void linkRegions()
152 foreach (Region r in regionList)
163 for (int t = 1; spaceOpen(x, y - t); t++)
165 if ( regions[x, y] != regions[x, y - t] )
167 regionList[regions[x, y]].AddVisible(regions[x, y - t]);
171 for (int t = 1; spaceOpen(x - t, y); t++)
173 if ( regions[x, y] != regions[x - t, y] )
175 regionList[regions[x, y]].AddVisible(regions[x - t, y]);
179 for (int t = 1; spaceOpen(x - t, y - t); t++)
181 if (regions[x, y] != regions[x - t, y - t])
183 regionList[regions[x, y]].AddVisible(regions[x - t, y - t]);
191 for (int t = 1; spaceOpen(x, y - t); t++)
193 if (regions[x, y] != regions[x, y - t])
195 regionList[regions[x, y]].AddVisible(regions[x, y - t]);
199 for (int t = 1; spaceOpen(x + t, y); t++)
201 if (regions[x, y] != regions[x + t, y])
203 regionList[regions[x, y]].AddVisible(regions[x + t, y]);
207 for (int t = 1; spaceOpen(x + t, y - t); t++)
209 if (regions[x, y] != regions[x + t, y - t])
211 regionList[regions[x, y]].AddVisible(regions[x + t, y - t]);
219 for (int t = 1; spaceOpen(x, y + t); t++)
221 if (regions[x, y] != regions[x, y + t])
223 regionList[regions[x, y]].AddVisible(regions[x, y + t]);
227 for (int t = 1; spaceOpen(x + t, y); t++)
229 if (regions[x, y] != regions[x + t, y])
231 regionList[regions[x, y]].AddVisible(regions[x + t, y]);
235 for (int t = 1; spaceOpen(x + t, y + t); t++)
237 if (regions[x, y] != regions[x + t, y + t])
239 regionList[regions[x, y]].AddVisible(regions[x + t, y + t]);
247 for (int t = 1; spaceOpen(x, y + t); t++)
249 if (regions[x, y] != regions[x, y + t])
251 regionList[regions[x, y]].AddVisible(regions[x, y + t]);
255 for (int t = 1; spaceOpen(x - t, y); t++)
257 if (regions[x, y] != regions[x - t, y])
259 regionList[regions[x, y]].AddVisible(regions[x - t, y]);
263 for (int t = 1; spaceOpen(x - t, y + t); t++)
265 if (regions[x, y] != regions[x - t, y + t])
267 regionList[regions[x, y]].AddVisible(regions[x - t, y + t]);
273 //for testing print the region grid to the console
274 public void printRegions()
276 Console.WriteLine("--Printing Regions--");
277 for (int y = 0; y < regions.GetLength(1); y++)
279 for (int x = 0; x < regions.GetLength(0); x++)
281 Console.Write(regions[x, y]);
283 Console.WriteLine("");
289 /// a chuck of the map that is at most 5x5 used to determine line of sight
293 List<int> visibleRegions; //other regions that are in this regions sight
299 int left, right, top, bottom;
301 public Region(int _label)
304 visibleRegions = new List<int>();
307 public void AddVisible(int region)
309 if(!visibleRegions.Contains(region))
310 visibleRegions.Add(region);
313 public void CalcCenter()
315 if (right != left) centerX = right + (right - left) / 2;
316 else centerX = right;
317 if (top != bottom) centerY = top + (bottom - top) / 2;
324 set { left = value; }
328 get { return right; }
329 set { right = value; }
338 get { return bottom; }
339 set { bottom = value; }
342 public Point Center { get { return new Point(centerX, centerY); } }
343 public int Label { get { return label; } }
345 public List<int> VisibleRegions { get { return visibleRegions; } }