//--------------------------------------------------------------------------------------------------------------------------------------------------- // // Copyright (C)2007 DarkWynter Studios. All rights reserved. // //--------------------------------------------------------------------------------------------------------------------------------------------------- // {Contact : darkwynter.com for licensing information //--------------------------------------------------------------------------------------------------------------------------------------------------- namespace ElementalGame.GameObjects { #region Using Statements using System; using System.Collections; using System.Collections.Generic; using Microsoft.Xna.Framework; using Microsoft.Xna.Framework.Audio; using Microsoft.Xna.Framework.Content; using Microsoft.Xna.Framework.Graphics; using Microsoft.Xna.Framework.Input; using Microsoft.Xna.Framework.Storage; using System.Xml; using System.Diagnostics; using Physics; using Globals; #endregion public class LookupMap { #region Attributes private LinkedList[,] lookupMap; private LinkedList[,] playerMap; private LinkedList returnList; private List dynamicList; private int mapWidth; private int mapHeight; #endregion #region Methods public LookupMap() { } public LookupMap(int width, int height) { mapWidth = width; mapHeight = height; lookupMap = new LinkedList[mapWidth, mapHeight]; for (int x = 0; x < mapWidth; x++) { for (int z = 0; z < mapHeight; z++) { lookupMap[x, z] = new LinkedList(); } } playerMap = new LinkedList[mapWidth, mapWidth]; for (int x = 0; x < mapWidth; x++) { for (int z = 0; z < mapHeight; z++) { playerMap[x, z] = new LinkedList(); } } returnList = new LinkedList(); dynamicList = new List(); } private bool UpdatePosition(Mass mass) { if (((int)mass.currentPosition.X / Statics.terrainScaleFactor != (int)mass.lastPosition.X / Statics.terrainScaleFactor) || ((int)mass.currentPosition.Z / Statics.terrainScaleFactor != (int)mass.lastPosition.Z / Statics.terrainScaleFactor)) { RemoveLast(mass); RemoveCurrent(mass); switch (mass.objectType) { case Enums.ObjectType.PLAYER: { playerMap[(int)mass.currentPosition.X / Statics.terrainScaleFactor, (int)mass.currentPosition.Z / Statics.terrainScaleFactor].AddLast(mass); break; } default: { lookupMap[(int)mass.currentPosition.X / Statics.terrainScaleFactor, (int)mass.currentPosition.Z / Statics.terrainScaleFactor].AddLast(mass); break; } } return true; } return false; } public LinkedList GetCollisionObjects(Mass mass) { // Get Min and Max search area positions int xMin = (int)mass.currentPosition.X / Statics.terrainScaleFactor - Statics.GameSettings.collisionSearchArea; int zMin = (int)mass.currentPosition.Z / Statics.terrainScaleFactor - Statics.GameSettings.collisionSearchArea; int xMax = (int)mass.currentPosition.X / Statics.terrainScaleFactor + Statics.GameSettings.collisionSearchArea; int zMax = (int)mass.currentPosition.Z / Statics.terrainScaleFactor + Statics.GameSettings.collisionSearchArea; // Bound Checking if (xMin < 0) { xMin = 0; } if (xMax >= mapWidth) { xMax = mapWidth - 1; } if (zMin < 0) { zMin = 0; } if (zMax >= mapHeight) { zMax = mapHeight - 1; } returnList.Clear(); // Concatenate a list of objects within the search area for (int currentX = xMin; currentX <= xMax; currentX++) { for (int currentZ = zMin; currentZ <= zMax; currentZ++) { if (lookupMap[currentX, currentZ].Count > 0) { foreach (Mass massObj in lookupMap[currentX, currentZ]) { if (massObj != null && massObj.gameObjectPointer != null && massObj != mass) { returnList.AddLast(massObj); } } } if (playerMap[currentX, currentZ].Count > 0) { foreach (Mass massObj in playerMap[currentX, currentZ]) { if (massObj != null && massObj.gameObjectPointer != null && massObj != mass) { Player player = (Player)massObj.gameObjectPointer; if (player.IsAlive()) { returnList.AddLast(massObj); } } } } } } // Don't return the object being checked for //while (returnList.Contains(mass)) //{ // returnList.Remove(mass); //} // Return the list of local objects return returnList; } public void GetDrawObjects(Mass mass, LinkedList drawList) { // Get Min and Max search area positions int xMin = (int)mass.currentPosition.X / Statics.terrainScaleFactor - Statics.GameSettings.drawSearchArea; int zMin = (int)mass.currentPosition.Z / Statics.terrainScaleFactor - Statics.GameSettings.drawSearchArea; int xMax = (int)mass.currentPosition.X / Statics.terrainScaleFactor + Statics.GameSettings.drawSearchArea; int zMax = (int)mass.currentPosition.Z / Statics.terrainScaleFactor + Statics.GameSettings.drawSearchArea; // Bound Checking if (xMin < 0) { xMin = 0; } if (xMax >= mapWidth) { xMax = mapWidth - 1; } if (zMin < 0) { zMin = 0; } if (zMax >= mapHeight) { zMax = mapHeight - 1; } drawList.Clear(); // Concatenate a list of objects within the search area for (int currentX = xMin; currentX <= xMax; currentX++) { for (int currentZ = zMin; currentZ <= zMax; currentZ++) { if (lookupMap[currentX, currentZ].Count > 0) { foreach (Mass massObj in lookupMap[currentX, currentZ]) { if (massObj != null && massObj.gameObjectPointer != null && massObj != mass) { #if !XBOX360 if (massObj.objectType == Enums.ObjectType.GPU_OBJECT || massObj.objectType == Enums.ObjectType.PROP || massObj.objectType == Enums.ObjectType.KEY|| massObj.objectType == Enums.ObjectType.PORTAL|| massObj.objectType == Enums.ObjectType.PARTICLE) { continue; } #endif drawList.AddLast(massObj); } } } if (playerMap[currentX, currentZ].Count > 0) { foreach (Mass massObj in playerMap[currentX, currentZ]) { if (massObj != null && massObj.gameObjectPointer != null && massObj != mass) { Player player = (Player)massObj.gameObjectPointer; if (player.IsAlive()) { drawList.AddLast(massObj); } } } } } } // Don't return the object being checked for //while (drawList.Contains(mass)) //{ // drawList.Remove(mass); //} //// Return the list of local objects //return returnList; } // Return the number of objects in the list private int Count() { int count = 0; for (int i = 0; i < mapWidth; i++) { for (int j = 0; j < mapHeight; j++) { if (playerMap[i, j].Count > 0) { count += playerMap[i, j].Count; } } } return count; } public void RemoveCurrent(Mass mass) { switch (mass.objectType) { case Enums.ObjectType.PLAYER: { while (playerMap[(int)mass.currentPosition.X / Statics.terrainScaleFactor, (int)mass.currentPosition.Z / Statics.terrainScaleFactor].Contains(mass)) { playerMap[(int)mass.currentPosition.X / Statics.terrainScaleFactor, (int)mass.currentPosition.Z / Statics.terrainScaleFactor].Remove(mass); } break; } default: { while (lookupMap[(int)mass.currentPosition.X / Statics.terrainScaleFactor, (int)mass.currentPosition.Z / Statics.terrainScaleFactor].Contains(mass)) { lookupMap[(int)mass.currentPosition.X / Statics.terrainScaleFactor, (int)mass.currentPosition.Z / Statics.terrainScaleFactor].Remove(mass); } break; } } } public void RemoveLast(Mass mass) { switch (mass.objectType) { case Enums.ObjectType.PLAYER: { while (playerMap[(int)mass.lastPosition.X / Statics.terrainScaleFactor, (int)mass.lastPosition.Z / Statics.terrainScaleFactor].Contains(mass)) { playerMap[(int)mass.lastPosition.X / Statics.terrainScaleFactor, (int)mass.lastPosition.Z / Statics.terrainScaleFactor].Remove(mass); } break; } default: { while (lookupMap[(int)mass.lastPosition.X / Statics.terrainScaleFactor, (int)mass.lastPosition.Z / Statics.terrainScaleFactor].Contains(mass)) { lookupMap[(int)mass.lastPosition.X / Statics.terrainScaleFactor, (int)mass.lastPosition.Z / Statics.terrainScaleFactor].Remove(mass); } break; } } } public void SetPosition(Mass mass) { switch (mass.objectType) { case Enums.ObjectType.PLAYER: { if (!playerMap[(int)mass.lastPosition.X / Statics.terrainScaleFactor, (int)mass.lastPosition.Z / Statics.terrainScaleFactor].Contains(mass)) { playerMap[(int)mass.lastPosition.X / Statics.terrainScaleFactor, (int)mass.lastPosition.Z / Statics.terrainScaleFactor].AddLast(mass); } break; } default: { lookupMap[(int)mass.lastPosition.X / Statics.terrainScaleFactor, (int)mass.lastPosition.Z / Statics.terrainScaleFactor].AddLast(mass); break; } } } public LinkedList GetListXZ(int x, int z) { return lookupMap[x, z]; } public void AddDynamic(Mass mass) { if (!dynamicList.Contains(mass)) { dynamicList.Add(mass); } } public void RemoveDynamic(Mass mass) { while (dynamicList.Contains(mass)) { dynamicList.Remove(mass); } } public List GetDynamicList() { return dynamicList; } public void UpdateDynamic(ObjectLibrary objectLibrary) { for (int i = 0; i < dynamicList.Count; i++) { if (dynamicList[i].gameObjectPointer == null) { RemoveDynamic(dynamicList[i]); i--; continue; } dynamicList[i].gameObjectPointer.Update(ref objectLibrary); if (!dynamicList[i].isMoving) { RemoveDynamic(dynamicList[i]); i--; } else { UpdatePosition(dynamicList[i]); } } } public void AddRange(List newMasses) { dynamicList.AddRange(newMasses); } public bool DynamicContains(Mass mass) { if (dynamicList.Contains(mass)) { return true; } return false; } #endregion } }