public bool RestartPathing(SmartEntity troopEntity, out bool found, bool ignoreWall)
        {
            ShooterComponent   shooterComp = troopEntity.ShooterComp;
            IShooterVO         shooterVO   = shooterComp.ShooterVO;
            TroopComponent     troopComp   = troopEntity.TroopComp;
            TeamComponent      teamComp    = troopEntity.TeamComp;
            ITroopDeployableVO troopType   = troopComp.TroopType;
            uint            maxAttackRange = this.GetMaxAttackRange(troopEntity, shooterComp.Target);
            PathTroopParams troopParams    = new PathTroopParams
            {
                TroopWidth            = troopEntity.SizeComp.Width,
                DPS                   = shooterVO.DPS,
                MinRange              = shooterVO.MinAttackRange,
                MaxRange              = maxAttackRange,
                MaxSpeed              = troopComp.SpeedVO.MaxSpeed,
                PathSearchWidth       = troopType.PathSearchWidth,
                IsMelee               = shooterComp.IsMelee,
                IsOverWall            = shooterVO.OverWalls,
                IsHealer              = troopType.IsHealer,
                SupportRange          = troopType.SupportFollowDistance,
                ProjectileType        = shooterVO.ProjectileType,
                CrushesWalls          = troopType.CrushesWalls,
                IsTargetShield        = GameUtils.IsEntityShieldGenerator(troopEntity.ShooterComp.Target),
                TargetInRangeModifier = troopType.TargetInRangeModifier
            };
            PathBoardParams boardParams = new PathBoardParams
            {
                IgnoreWall   = (teamComp.IsDefender() || ignoreWall),
                Destructible = teamComp.CanDestructBuildings()
            };

            return(this.StartPathing(troopEntity, shooterComp.Target, troopEntity.TransformComp, true, out found, -1, troopParams, boardParams, true, false));
        }
        public bool StartPathing(SmartEntity troop, SmartEntity target, TransformComponent transform, bool clampPathLength, out bool found, int rangeOverride, PathTroopParams troopParams, PathBoardParams boardParams, bool isRepathing, bool allowTroopFanning)
        {
            if (troop == null || target == null)
            {
                found = false;
                return(true);
            }
            if (this.IsPathingOngoing())
            {
                found = false;
                return(false);
            }
            boardParams.IgnoreWall = (boardParams.IgnoreWall || troop.TroopComp.TroopType.IsFlying);
            this.troop             = troop;
            this.target            = target;
            this.noWall            = boardParams.IgnoreWall;
            this.crushesWalls      = troopParams.CrushesWalls;
            this.transform         = transform;
            SmartEntity         smartEntity    = (SmartEntity)transform.Entity;
            int                 x              = transform.X;
            int                 z              = transform.Z;
            BoardCell <Entity>  cellAt         = this.boardController.Board.GetCellAt(x, z);
            BoardCell <Entity>  boardCell      = null;
            DamageableComponent damageableComp = target.DamageableComp;
            ShooterComponent    shooterComp    = troop.ShooterComp;

            this.pathingComp = smartEntity.PathingComp;
            BoardCell <Entity> boardCell2;

            if ((this.pathingComp != null & isRepathing) && this.pathingComp.TargetCell != null && this.pathingComp.EndCell != null && damageableComp != null)
            {
                boardCell2 = this.pathingComp.TargetCell;
                boardCell  = this.pathingComp.EndCell;
            }
            else if (damageableComp != null)
            {
                uint maxRange = (uint)((rangeOverride >= 0) ? rangeOverride : ((int)shooterComp.ShooterVO.MaxAttackRange));
                boardCell = damageableComp.FindAttackCell(maxRange, troopParams.TroopWidth, x, z, allowTroopFanning);
                int x2;
                int z2;
                damageableComp.GetCenterPosition(out x2, out z2);
                boardCell2 = this.boardController.Board.GetCellAt(x2, z2);
            }
            else
            {
                TransformComponent transformComp = target.TransformComp;
                boardCell2 = this.boardController.Board.GetCellAt(transformComp.CenterGridX(), transformComp.CenterGridZ());
                int  squaredDistanceToTarget = GameUtils.GetSquaredDistanceToTarget(shooterComp, target);
                bool flag = (long)squaredDistanceToTarget > (long)((ulong)shooterComp.MaxAttackRangeSquared);
                if (boardCell2 != cellAt && !troopParams.IsHealer)
                {
                    if (flag)
                    {
                        int x3          = boardCell2.X - cellAt.X;
                        int y           = boardCell2.Z - cellAt.Z;
                        int num         = IntMath.Atan2Lookup(x3, y) * 180 / 16384;
                        int targetCount = target.TroopComp.TargetCount;
                        int num2        = (int)((troopParams.MaxRange > 1u) ? (troopParams.MaxRange - 1u) : 1u);
                        for (int i = num2; i > 0; i--)
                        {
                            if (boardCell != null)
                            {
                                break;
                            }
                            int num3 = i * 3 + 1;
                            int num4 = 180 / num3;
                            for (int j = 0; j < num3; j++)
                            {
                                int num5       = (j + targetCount) % num3;
                                int twiceAngle = (num + 90 + num5 * num4) % 360 * 2;
                                int x4         = boardCell2.X + IntMath.cosLookup(twiceAngle) * i / 1024;
                                int z3         = boardCell2.Z + IntMath.sinLookup(twiceAngle) * i / 1024;
                                boardCell = this.boardController.Board.GetClampedToBoardCellAt(x4, z3, troopParams.TroopWidth);
                                if ((boardCell.Children == null || boardCell.Children.Count == 0) && boardCell.Clearance >= troopParams.TroopWidth)
                                {
                                    break;
                                }
                                boardCell = null;
                            }
                        }
                    }
                    else
                    {
                        boardCell = cellAt;
                    }
                }
                if (boardCell == null)
                {
                    boardCell = boardCell2;
                    if (boardCell.Clearance < troopParams.TroopWidth)
                    {
                        this.pathingComp = null;
                        found            = false;
                        return(false);
                    }
                }
            }
            WalkerComponent walkerComp = smartEntity.WalkerComp;

            if (this.pathingComp == null)
            {
                this.pathingComp = new PathingComponent(walkerComp.SpeedVO.MaxSpeed, target);
            }
            else
            {
                this.pathingComp.Reset();
                this.pathingComp.MaxSpeed = walkerComp.SpeedVO.MaxSpeed;
                this.pathingComp.Target   = target;
            }
            this.pathingComp.TargetCell = boardCell2;
            this.pathingComp.EndCell    = boardCell;
            int maxLength = -1;
            BattleController battleController = Service.Get <BattleController>();

            if (clampPathLength && (battleController == null || battleController.GetCurrentBattle().Type == BattleType.Pvp || battleController.GetCurrentBattle().Type == BattleType.ClientBattle))
            {
                int num6 = IntMath.FastDist(cellAt.X, cellAt.Z, boardCell2.X, boardCell2.Z);
                maxLength = 2 * num6 / 1024 + 2;
            }
            this.path = new Path(cellAt, boardCell, boardCell2, maxLength, troopParams, boardParams);
            this.UpdatePathing(out found);
            return(true);
        }
Beispiel #3
0
        public Path(BoardCell fromCell, BoardCell toCell, BoardCell targetAt, int maxLength, PathTroopParams troopParams, PathBoardParams boardParams)
        {
            this.pathCells     = new BoardCellDynamicArray(64);
            this.scratchCells  = new BoardCellDynamicArray(64);
            this.turns         = new BoardCellDynamicArray(64);
            this.turnDistances = new List <int>(64);
            BoardController boardController = Service.BoardController;

            this.board                 = boardController.Board;
            this.pathingManager        = Service.PathingManager;
            this.startCell             = fromCell;
            this.destCell              = toCell;
            this.targetCell            = targetAt;
            this.NoWall                = (boardParams.IgnoreWall || troopParams.CrushesWalls);
            this.crushesWalls          = troopParams.CrushesWalls;
            this.destructible          = boardParams.Destructible;
            this.isHealer              = troopParams.IsHealer;
            this.TroopWidth            = troopParams.TroopWidth;
            this.damagePerSecond       = troopParams.DPS;
            this.maxShooterRange       = troopParams.MaxRange;
            this.targetInRangeModifier = troopParams.TargetInRangeModifier;
            if (this.isHealer && this.maxShooterRange > troopParams.SupportRange)
            {
                this.maxShooterRange = troopParams.SupportRange;
            }
            this.minShooterRange    = troopParams.MinRange;
            this.maxSpeed           = troopParams.MaxSpeed;
            this.heristicMultiplier = (int)troopParams.PathSearchWidth;
            this.maxPathLength      = ((!this.isHealer) ? maxLength : -1);
            this.melee                        = troopParams.IsMelee;
            this.overWalls                    = troopParams.IsOverWall;
            this.projectileType               = troopParams.ProjectileType;
            this.isTargetShield               = troopParams.IsTargetShield;
            this.openCells                    = new HeapPriorityQueue(boardController.GetPriorityQueueSize());
            this.curPathingCell               = this.pathingManager.GetPathingCell();
            this.curPathingCell.Cell          = this.startCell;
            this.startCell.PathInfo           = this.curPathingCell;
            this.curPathingCell.InRange       = this.InRangeOfTarget(this.startCell);
            this.curPathingCell.RemainingCost = this.HeuristicDiagonal(this.startCell, this.destCell);
            this.curPathingCell.PathLength    = 0;
            this.curPathingCell.PastCost      = 0;
            this.curPathingCell.InClosedSet   = true;
        }