示例#1
0
 /// <summary>
 /// Move to ceter tile position in speed
 /// </summary>
 /// <param name="centerTilePosition"></param>
 /// <param name="speed"></param>
 public void MoveTo(Vector2 centerTilePosition, int speed)
 {
     _moveToBeginDestination = Map.ToPixelPosition(centerTilePosition) -
                               GetHalfViewSize();
     _moveSpeed = speed;
     IsInMoveTo = true;
 }
示例#2
0
        private static void AddVTypeFixedPOsitionMagicSprite(Character user, Magic magic, Vector2 origin, Vector2 destination, bool destroyOnEnd)
        {
            var direction      = destination - origin;
            var directionIndex = Utils.GetDirectionIndex(direction, 8);
            var count          = 3;

            if (magic.CurrentLevel > 3)
            {
                count += ((magic.CurrentLevel - 1) / 3) * 2;
            }
            var orgTile = PathFinder.FindNeighborInDirection(Map.ToTilePosition(origin), directionIndex);

            AddMagicSprite(GetFixedPositionMagicSprite(user, magic, Map.ToPixelPosition(orgTile), destroyOnEnd));
            const float magicDelayMilliseconds = 60f;
            var         leftVTile  = orgTile;
            var         rightVTile = orgTile;

            for (var i = 1; i < count; i++)
            {
                leftVTile  = PathFinder.FindNeighborInDirection(leftVTile, (directionIndex + 7) % 8);
                rightVTile = PathFinder.FindNeighborInDirection(rightVTile, (directionIndex + 1) % 8);
                AddWorkItem(new WorkItem(i * magicDelayMilliseconds,
                                         GetFixedPositionMagicSprite(user, magic, Map.ToPixelPosition(leftVTile), destroyOnEnd)));
                AddWorkItem(new WorkItem(i * magicDelayMilliseconds,
                                         GetFixedPositionMagicSprite(user, magic, Map.ToPixelPosition(rightVTile), destroyOnEnd)));
            }
        }
示例#3
0
        private static void AddRegionFileMagicSprite(Character user, Magic magic, Vector2 origin, Vector2 destination, bool destroyOnEnd)
        {
            if (magic.RegionFile == null)
            {
                return;
            }

            var direction      = destination - origin;
            var directionIndex = Utils.GetDirectionIndex(direction, 8);
            var items          = magic.RegionFile.ContainsKey(directionIndex)
                ? magic.RegionFile[directionIndex]
                : magic.RegionFile[0];

            //Make destination at tile center
            destination = Map.ToPixelPosition(Map.ToTilePosition(destination));
            foreach (var item in items)
            {
                var magicSprite = GetFixedPositionMagicSprite(user, magic, destination + item.Offset, destroyOnEnd);
                if (item.Delay > 0)
                {
                    AddWorkItem(new WorkItem(item.Delay, magicSprite));
                }
                else
                {
                    AddMagicSprite(magicSprite);
                }
            }
        }
示例#4
0
        private static void FillItems(List <Item> items, Vector2 beginPos, Layer layer, Dictionary <int, List <int> > delayInfo)
        {
            var beginPixelPosition = Map.ToPixelPosition(beginPos, false);

            for (var h = 0; h < layer.Height; h++)
            {
                for (var w = 0; w < layer.Width; w++)
                {
                    var tileIndex = layer.Data[w + h * layer.Width];
                    if (tileIndex == 0)
                    {
                        continue;
                    }
                    var offset = Map.ToPixelPosition(w, h, false) - beginPixelPosition;
                    if (delayInfo.ContainsKey(tileIndex))
                    {
                        items.AddRange(delayInfo[tileIndex].Select(delay => new Item(offset, delay)));
                    }
                    else
                    {
                        items.Add(new Item(offset, 0));
                    }
                }
            }
        }
示例#5
0
        /// <summary>
        /// Bounce at wall, find wall tiles.
        /// </summary>
        /// <param name="direction"></param>
        /// <param name="worldPosition"></param>
        /// <param name="targetTilePosition"></param>
        /// <returns>Bouncing direction</returns>
        public static Vector2 BouncingAtWall(Vector2 direction, Vector2 worldPosition, Vector2 targetTilePosition)
        {
            if (direction == Vector2.Zero)
            {
                return(direction);
            }
            var dir       = Utils.GetDirectionIndex(direction, 8);
            var checks    = new[] { (dir + 2) % 8, (dir + 6) % 8, (dir + 1) % 8, (dir + 7) % 8 };
            var get       = 8;
            var neighbors = FindAllNeighbors(targetTilePosition);

            for (var i = 0; i < checks.Count(); i++)
            {
                if (Globals.TheMap.IsObstacleForMagic(neighbors[checks[i]]))
                {
                    get = checks[i];
                    break;
                }
            }
            if (get == 8)
            {
                return(BouncingAtPoint(direction, worldPosition, Map.ToPixelPosition(targetTilePosition)));
            }
            var normal = Map.ToPixelPosition(targetTilePosition) - Map.ToPixelPosition(neighbors[get]);

            normal = Vector2.Normalize(new Vector2(-normal.Y, normal.X));
            return(Vector2.Reflect(direction, normal));
        }
示例#6
0
        /// <summary>
        /// Get line path without care obstacle.
        /// </summary>
        /// <param name="startTile">Start tile positon</param>
        /// <param name="endTile">End tile positon</param>
        /// <param name="maxTry">Max strep</param>
        /// <param name="tilePositon">If true, path position in path list is tile position.Otherwise is postion in world.</param>
        /// <returns>Path positition in world list.</returns>
        public static LinkedList <Vector2> GetLinePath(Vector2 startTile, Vector2 endTile, int maxTry, bool tilePositon = false)
        {
            if (startTile == endTile)
            {
                return(null);
            }

            var path     = new LinkedList <Vector2>();
            var frontier = new C5.IntervalHeap <Node <Vector2> >();

            frontier.Add(new Node <Vector2>(startTile, 0f));
            while (!frontier.IsEmpty)
            {
                if (maxTry-- < 0)
                {
                    break;
                }
                var current = frontier.DeleteMin().Location;
                path.AddLast(tilePositon? current : Map.ToPixelPosition(current));
                if (current == endTile)
                {
                    break;
                }
                foreach (var neighbor in FindAllNeighbors(current))
                {
                    frontier.Add(new Node <Vector2>(neighbor, GetTilePositionCost(neighbor, endTile)));
                }
            }
            return(path);
        }
示例#7
0
        public Texture2D GetTileTextureAndRegion(int x, int y, int layer, ref Rectangle region)
        {
            if (!IsOk)
            {
                return(null);
            }
            var texture = GetTileTexture(x, y, layer);

            if (texture != null)
            {
                var position = Map.ToPixelPosition(x, y) - new Vector2(texture.Width / 2f, texture.Height - 16f);
                region = new Rectangle((int)position.X, (int)position.Y, texture.Width, texture.Height);
            }
            return(texture);
        }
示例#8
0
 private static LinkedList <Vector2> GetPath(Dictionary <Vector2, Vector2> cameFrom, Vector2 startTile,
                                             Vector2 endTile)
 {
     if (cameFrom.ContainsKey(endTile))
     {
         var path    = new LinkedList <Vector2>();
         var current = endTile;
         path.AddFirst(Map.ToPixelPosition(current));
         while (current != startTile)
         {
             current = cameFrom[current];
             path.AddFirst(Map.ToPixelPosition(current));
         }
         return(path);
     }
     return(null);
 }
示例#9
0
        private bool Init(Magic belongMagic, Character belongCharacter, Vector2 positionInWorld, float velocity,
                          Vector2 moveDirection, bool destroyOnEnd)
        {
            if (belongMagic == null || belongCharacter == null)
            {
                _isDestroyed = true;
                return(false);
            }

            if (belongMagic.NoExplodeWhenLifeFrameEnd > 0)
            {
                destroyOnEnd = false;
            }
            else if (belongMagic.ExplodeWhenLifeFrameEnd > 0)
            {
                destroyOnEnd = true;
            }

            _destnationPixelPosition = positionInWorld;
            var texture = belongMagic.FlyingImage;

            switch (belongMagic.MoveKind)
            {
            case 15:
                texture = belongMagic.SuperModeImage;
                break;

            case 20:
                positionInWorld = Map.ToPixelPosition(belongCharacter.TilePosition);
                break;

            case 21:
            {
                var player = belongCharacter as Player;
                if (player != null &&
                    player.ControledCharacter != null)
                {
                    player.ControledCharacter.ControledMagicSprite = this;
                }
                else
                {
                    throw new Exception("Magic kind 21 internal error.");
                }
            }
            break;

            case 22:    //Summon
            {
                var tilePosition = Map.ToTilePosition(positionInWorld);
                var finded       = PathFinder.FindNonobstacleNeighborOrItself(belongCharacter, ref tilePosition);
                if (finded)
                {
                    positionInWorld = Map.ToPixelPosition(tilePosition);
                }
                else
                {
                    _isDestroyed = true;
                    break;
                }
                if (belongCharacter.SummonedNpcsCount >= belongMagic.MaxCount)
                {
                    //Reach max count
                    belongCharacter.RemoveFirstSummonedNpc();
                }
                var npc = NpcManager.AddNpc(belongMagic.NpcFile,
                                            (int)tilePosition.X,
                                            (int)tilePosition.Y,
                                            Utils.GetDirectionIndex(positionInWorld - belongCharacter.PositionInWorld, 8));
                belongCharacter.AddSummonedNpc(npc);
                if (belongCharacter.IsPlayer || belongCharacter.IsFighterFriend)
                {
                    npc.Relation = (int)Character.RelationType.Friend;
                }
                else
                {
                    npc.Kind     = (int)Character.CharacterKind.Fighter;
                    npc.Relation = (int)Character.RelationType.Enemy;
                }
                npc.SummonedByMagicSprite = this;
                _summonedNpc = npc;
            }
            break;
            }
            if (belongMagic.CarryUser > 0)
            {
                belongCharacter.MovedByMagicSprite = this;
            }
            Set(positionInWorld, velocity, texture, 0);
            BelongMagic     = belongMagic;
            BelongCharacter = belongCharacter;
            MoveDirection   = moveDirection;
            _destroyOnEnd   = destroyOnEnd;
            SetDirection(MoveDirection);
            _lastUserWorldPosition    = belongCharacter.PositionInWorld;
            _rangeElapsedMilliseconds = belongMagic.RangeTimeInerval;

            if (BelongMagic.MeteorMove > 0)
            {
                _waitMilliSeconds = Globals.TheRandom.Next(1000);
                var dir  = (BelongMagic.MeteorMoveDir > 7) ? Globals.TheRandom.Next(8) : BelongMagic.MeteorMoveDir;
                var path = new LinkedList <Vector2>();
                path.AddFirst(positionInWorld);
                var tile = Map.ToTilePosition(positionInWorld, false);
                for (var i = 0; i <= BelongMagic.MeteorMove; i++)
                {
                    tile = PathFinder.FindNeighborInDirection(tile, dir);
                    path.AddFirst(Map.ToPixelPosition(tile, false));
                }
                SetPath(path);
                PositionInWorld = path.First.Value;
                Velocity        = belongMagic.Speed * Globals.MagicBasespeed;
            }

            return(true);
        }
示例#10
0
        public static void Update(GameTime gameTime)
        {
            var elapsedMilliseconds = (float)gameTime.ElapsedGameTime.TotalMilliseconds;

            for (var node = _workList.First; node != null;)
            {
                var item = node.Value;
                var next = node.Next;
                item.LeftMilliseconds -= elapsedMilliseconds;
                if (item.LeftMilliseconds <= 0)
                {
                    AddMagicSprite(item.TheSprite);
                    _workList.Remove(node);
                }
                node = next;
            }

            for (var node = _magicSprites.First; node != null;)
            {
                var sprite = node.Value;
                var next   = node.Next;
                if (sprite.IsDestroyed)
                {
                    RemoveMagicSprite(node);
                }
                else
                {
                    sprite.Update(gameTime);
                }
                node = next;
            }

            for (var node = _solideMagicSprites.First; node != null;)
            {
                var sprite = node.Value;
                var next   = node.Next;
                if (sprite.IsInDestroy || sprite.IsDestroyed)
                {
                    _solideMagicSprites.Remove(node);
                }
                node = next;
            }

            for (var node = _effectSprites.First; node != null;)
            {
                var sprite = node.Value;
                var next   = node.Next;
                sprite.Update(gameTime);
                if (!sprite.IsInPlaying)
                {
                    _effectSprites.Remove(node);
                }
                node = next;
            }

            for (var node = _kind19Magics.First; node != null;)
            {
                var info = node.Value;
                var next = node.Next;
                if (info.LastTilePosition != info.BelongCharacter.TilePosition)
                {
                    AddFixedPositionMagicSprite(info.BelongCharacter, info.TheMagic, Map.ToPixelPosition(info.LastTilePosition), true);
                    info.LastTilePosition = info.BelongCharacter.TilePosition;
                }
                info.KeepMilliseconds -= elapsedMilliseconds;
                if (info.KeepMilliseconds <= 0)
                {
                    _kind19Magics.Remove(node);
                }
                node = next;
            }
        }
示例#11
0
        //Returned path is in pixel position
        public static LinkedList <Vector2> FindPathStep(Character finder, Vector2 startTile, Vector2 endTile, int stepCount)
        {
            if (finder == null)
            {
                return(null);
            }
            if (startTile == endTile)
            {
                return(null);
            }

            if (Globals.TheMap.IsObstacleForCharacter(endTile))
            {
                return(null);
            }

            var path   = new LinkedList <Vector2>();
            var visted = new LinkedList <Vector2>();

            var endPositon = Map.ToPixelPosition(endTile);

            path.AddLast(Map.ToPixelPosition(startTile));
            var current = startTile;
            var maxTry  = 100;// For performance

            while (maxTry-- > 0)
            {
                var direction  = Utils.GetDirectionIndex(endPositon - Map.ToPixelPosition(current), 8);
                var neighbors  = FindAllNeighbors(current);
                var removeList = GetObstacleIndexList(neighbors);
                var index      = -1;
                var list       = new int[]
                {
                    direction,
                    (direction + 1) % 8, (direction + 8 - 1) % 8,
                    (direction + 2) % 8, (direction + 8 - 2) % 8,
                    (direction + 3) % 8, (direction + 8 - 3) % 8,
                    (direction + 4) % 8
                };
                for (var i = 0; i < 8; i++)
                {
                    var position = neighbors[list[i]];
                    if (removeList.Contains(list[i]) ||
                        HasObstacle(finder, position) ||
                        visted.Contains(position))
                    {
                        continue;
                    }
                    index = list[i];
                    break;
                }
                if (index == -1)
                {
                    break;
                }
                current = neighbors[index];
                path.AddLast(Map.ToPixelPosition(current));
                visted.AddLast(current);

                if (path.Count > stepCount || current == endTile)
                {
                    break;
                }
            }

            return(path.Count < 2 ? null : path);;
        }
示例#12
0
 public static float GetTilePositionCost(Vector2 fromTile, Vector2 toTile)
 {
     return(Vector2.Distance(Map.ToPixelPosition(fromTile), Map.ToPixelPosition(toTile)));
 }