using System; using System.Collections.Generic; using System.Linq; using System.Text; using Microsoft.Xna.Framework; using Microsoft.Xna.Framework.Content; using Microsoft.Xna.Framework.Graphics; namespace CarFire { public enum AiState { Standing, Pacing, Chasing, Dazed, Fighting, Retreating } public class SaberMonster : IMonster { public SaberMonster(char identifier, Point position, Dictionary info, Game game) { mId = identifier; mMotion = new MovementManager(position); mGame = game; string speedString; if (info.TryGetValue("speed", out speedString)) { int? speed = Parse.Integer(speedString); if (speed != null) mMotion.Speed = speed.Value; } // Get the "idle path" coordinates loaded from the map. string idlePath; if (info.TryGetValue("path", out idlePath)) { string[] idlePathPoints = Parse.List(idlePath); foreach (string pathPoint in idlePathPoints) { Point? point = Parse.Coordinates(pathPoint); if (point != null) mIdlePath.Add(point.Value); } } StartPacing(); } public void StartPacing() { mState = AiState.Pacing; if (mIdlePath.Count == 0) return; // Determine the best (closest) waypoint to start at. mIdlePathIndex = 0; int closest = int.MaxValue; for (int i = 0; i < mIdlePath.Count; i++) { int distance = PathFinder.GetManhattanDistance(Coordinates, mIdlePath[i]); if (distance < closest) { mIdlePathIndex = i; closest = distance; } } PathFinder pathFinder = new PathFinder(mGame.Grid); mPath = new List(32); mPath.Add(Coordinates); mPath.AddRange(pathFinder.GetPath(mMotion.Coordinates, mIdlePath[mIdlePathIndex])); mPath.Add(mIdlePath[mIdlePathIndex]); mPathIndex = 0; } Direction GetDirectionToNextCell() { if (mPathIndex >= mPath.Count) { mIdlePathIndex++; PathFinder pathFinder = new PathFinder(mGame.Grid); mPath = new List(32); mPath.Add(Coordinates); mPath.AddRange(pathFinder.GetPath(mMotion.Coordinates, mIdlePath[mIdlePathIndex % mIdlePath.Count])); mPath.Add(mIdlePath[mIdlePathIndex % mIdlePath.Count]); mPathIndex = 0; } if (mPath[mPathIndex % mPath.Count] == mMotion.Coordinates) { mPathIndex++; mPathDirection = MovementManager.GetDirection(mMotion.Coordinates, mPath[mPathIndex % mPath.Count]); } return mPathDirection; } #region IMonster Members public bool visible { get { throw new NotImplementedException(); } } #endregion #region ICharacter Members public void LoadContent(ContentManager contentManager) { mTexture = contentManager.Load("menuItem"); } public void Update(TimeSpan timeSpan) { if (mState == AiState.Pacing) { mMotion.Update(timeSpan, GetDirectionToNextCell()); } } public void Draw(SpriteBatch spriteBatch) { Rectangle position = mGame.State.Map.GetRectangleFromCoordinates(mMotion.Position); spriteBatch.Draw(mTexture, position, Color.White); } public int Health { get { throw new NotImplementedException(); } } public void causeDamageTo(int amount) { throw new NotImplementedException(); } public Vector2 Position { get { return mMotion.Position; } } public Point Coordinates { get { return mMotion.Coordinates; } } #endregion #region Private Variables Game mGame; char mId; MovementManager mMotion; List mIdlePath = new List(); int mIdlePathIndex; List mPath; int mPathIndex; Direction mPathDirection; AiState mState; Texture2D mTexture; #endregion } }