/// <summary>
        /// Renders the 8-directional sprite
        /// </summary>
        /// <param name="ihn">Ihn entity is contained in</param>
        /// <param name="spriteBatch">Spritebatch to draw with</param>
        /// <param name="entity">Entity to draw</param>
        public void Render(Ihn ihn, SpriteBatch spriteBatch, Entity entity)
        {
            var sprite = entity.GetComp <ComponentTopDownEightDirSprite>();
            var pos    = entity.GetComp <ComponentPosition>();
            var dir    = entity.GetComp <ComponentDirection>();
            int sizex  = Rsc.Load <Texture2D>(sprite.Texture).Width / 4;
            int sizey  = Rsc.Load <Texture2D>(sprite.Texture).Height / 2;

            if (entity.HasComp <ComponentSize>())
            {
                var size = entity.GetComp <ComponentSize>();
                sizex = size.Width;
                sizey = size.Height;
            }
            float Rotation = DirectionHelper.ToAngle(dir.Dir);

            spriteBatch.Draw(Rsc.Load <Texture2D>(sprite.Texture),
                             new Rectangle((int)pos.X - (int)ihn.CameraPos.X, (int)pos.Y - (int)ihn.CameraPos.Y, sizex, sizey),
                             new Rectangle(DirectionHelper.IsDiagonal(dir.Dir) ? Rsc.Load <Texture2D>(sprite.Texture).Width / 2 : 0, 0, Rsc.Load <Texture2D>(sprite.Texture).Width / 2, Rsc.Load <Texture2D>(sprite.Texture).Height),
                             Color.White,
                             MathHelper.ToRadians(Rotation - (DirectionHelper.IsDiagonal(dir.Dir) ? 45 : 0)),
                             new Vector2(Rsc.Load <Texture2D>(sprite.Texture).Width / 4, Rsc.Load <Texture2D>(sprite.Texture).Height / 2),
                             SpriteEffects.None,
                             0);
        }
Пример #2
0
        /// <summary>
        /// Finds path along a 2D grid
        /// </summary>
        /// <param name="solidityMap">2D array of solids</param>
        /// <param name="start">Vector of starting position</param>
        /// <param name="end">Vector of ending position</param>
        /// <returns>List of points to follow</returns>
        public static List <Vector2> FindPath(bool[,] solidityMap, Vector2 start, Vector2 end)
        {
            var finalPath = new List <Vector2>();

            if (!(start.X < solidityMap.GetLength(0) - 1 &&
                  start.X > 0 &&
                  start.Y < solidityMap.GetLength(1) - 1 &&
                  start.Y > 0 &&
                  end.X < solidityMap.GetLength(0) - 1 &&
                  end.X > 0 &&
                  end.Y < solidityMap.GetLength(1) - 1 &&
                  end.Y > 0))
            {
                return(finalPath);
            }
            var closed = new List <Node>();
            var open   = new List <Node> {
                new Node(start)
            };
            bool done        = false;
            Node currentNode = open[0];
            int  trials      = 0;

            while (!done && trials < 1000)
            {
                trials++;
                var lowestF = int.MaxValue;
                for (int i = 0; i < open.Count; i++)
                {
                    if (Math.Abs(open[i].Pos.X - end.X) + Math.Abs(open[i].Pos.Y - end.Y) < lowestF)
                    {
                        lowestF     = (int)(Math.Abs(open[i].Pos.X - end.X) + Math.Abs(open[i].Pos.Y - end.Y));
                        currentNode = open[i];
                    }
                }
                if (currentNode.Pos.X == end.X && currentNode.Pos.Y == end.Y)
                {
                    done = true;
                }
                else
                {
                    closed.Add(currentNode);
                    open.Remove(currentNode);
                    for (int i = -1; i <= 1; i++)
                    {
                        for (int j = -1; j <= 1; j++)
                        {
                            if ((i != 0 || j != 0) && !DirectionHelper.IsDiagonal(DirectionHelper.VectorToDirection(new Vector2(i, j))) &&
                                currentNode.Pos.X + i > 0 && currentNode.Pos.Y + j > 0 &&
                                currentNode.Pos.X + i < solidityMap.GetLength(0) &&
                                currentNode.Pos.Y + j < solidityMap.GetLength(1) &&
                                !solidityMap[(int)currentNode.Pos.X + i, (int)currentNode.Pos.Y + j])
                            {
                                bool isInClosed = false;
                                Node closedNode = null;
                                for (int k = 0; k < closed.Count; k++)
                                {
                                    if (closed[k].Pos.X == currentNode.Pos.X + i && closed[k].Pos.Y == currentNode.Pos.Y + j)
                                    {
                                        isInClosed = true;
                                        closedNode = closed[k];
                                        break;
                                    }
                                }
                                if (isInClosed && closedNode.G > currentNode.G + 1)
                                {
                                    closedNode.G      = currentNode.G + 1;
                                    closedNode.Parent = currentNode;
                                }
                                else if (!isInClosed)
                                {
                                    bool isInOpen = false;
                                    Node openNode = null;
                                    for (int k = 0; k < open.Count; k++)
                                    {
                                        if (open[k].Pos.X == currentNode.Pos.X + i && open[k].Pos.Y == currentNode.Pos.Y + j)
                                        {
                                            isInOpen = true;
                                            openNode = open[k];
                                            break;
                                        }
                                    }
                                    if (isInOpen && openNode.G > currentNode.G + 1)
                                    {
                                        openNode.G      = currentNode.G + 1;
                                        openNode.Parent = currentNode;
                                    }
                                    else if (!isInOpen)
                                    {
                                        Node n = new Node(new Vector2(currentNode.Pos.X + i, currentNode.Pos.Y + j), currentNode);
                                        n.G = currentNode.G + 1;
                                        open.Add(n);
                                        trials = 0;
                                    }
                                }
                            }
                        }
                    }
                }
            }
            while (currentNode.Parent != null)
            {
                finalPath.Add(currentNode.Pos);
                currentNode = currentNode.Parent;
            }
            finalPath.Add(currentNode.Pos);
            finalPath.Reverse();
            return(finalPath);
        }