public static PositionInfo GetBestPosition() { int posChecked = 0; int maxPosToCheck = 50; int posRadius = 50; int radiusIndex = 0; var extraDelayBuffer = ObjectCache.menuCache.cache["ExtraPingBuffer"].Cast <Slider>().CurrentValue; var extraEvadeDistance = ObjectCache.menuCache.cache["ExtraEvadeDistance"].Cast <Slider>().CurrentValue; SpellDetector.UpdateSpells(); CalculateEvadeTime(); if (ObjectCache.menuCache.cache["CalculateWindupDelay"].Cast <CheckBox>().CurrentValue) { var extraWindupDelay = Evade.lastWindupTime - EvadeUtils.TickCount; if (extraWindupDelay > 0) { extraDelayBuffer += (int)extraWindupDelay; } } extraDelayBuffer += (int)(Evade.avgCalculationTime); if (ObjectCache.menuCache.cache["HigherPrecision"].Cast <CheckBox>().CurrentValue) { maxPosToCheck = 150; posRadius = 25; } Vector2 heroPoint = ObjectCache.myHeroCache.serverPos2D; Vector2 lastMovePos = Game.CursorPos.LSTo2D(); List <PositionInfo> posTable = new List <PositionInfo>(); Spell lowestEvadeTimeSpell; var lowestEvadeTime = SpellDetector.GetLowestEvadeTime(out lowestEvadeTimeSpell); List <Vector2> fastestPositions = GetFastestPositions(); foreach (var pos in fastestPositions) //add the fastest positions into list of candidates { posTable.Add(InitPositionInfo(pos, extraDelayBuffer, extraEvadeDistance, lastMovePos, lowestEvadeTimeSpell)); } /*if (SpellDetector.spells.Count() == 1) * { * var sortedFastestTable = * posTable.OrderBy(p => p.posDangerLevel); * * if (sortedFastestTable.First() != null && sortedFastestTable.First().posDangerLevel > 0) * { * //use fastest * } * }*/ while (posChecked < maxPosToCheck) { radiusIndex++; int curRadius = radiusIndex * (2 * posRadius); int curCircleChecks = (int)Math.Ceiling((2 * Math.PI * (double)curRadius) / (2 * (double)posRadius)); for (int i = 1; i < curCircleChecks; i++) { posChecked++; var cRadians = (2 * Math.PI / (curCircleChecks - 1)) * i; //check decimals var pos = new Vector2((float)Math.Floor(heroPoint.X + curRadius * Math.Cos(cRadians)), (float)Math.Floor(heroPoint.Y + curRadius * Math.Sin(cRadians))); posTable.Add(InitPositionInfo(pos, extraDelayBuffer, extraEvadeDistance, lastMovePos, lowestEvadeTimeSpell)); } } IOrderedEnumerable <PositionInfo> sortedPosTable; if (ObjectCache.menuCache.cache["EvadeMode"].Cast <ComboBox>().CurrentValue == 1) { sortedPosTable = posTable.OrderBy(p => p.isDangerousPos) .ThenByDescending(p => p.intersectionTime) .ThenBy(p => p.posDangerLevel) .ThenBy(p => p.posDangerCount); fastEvadeMode = true; } else if (ObjectCache.menuCache.cache["FastEvadeActivationTime"].Cast <Slider>().CurrentValue > 0 && ObjectCache.menuCache.cache["FastEvadeActivationTime"].Cast <Slider>().CurrentValue + ObjectCache.gamePing + extraDelayBuffer > lowestEvadeTime) { sortedPosTable = posTable.OrderBy(p => p.isDangerousPos) .ThenByDescending(p => p.intersectionTime) .ThenBy(p => p.posDangerLevel) .ThenBy(p => p.posDangerCount); fastEvadeMode = true; } else { sortedPosTable = posTable.OrderBy(p => p.rejectPosition) .ThenBy(p => p.posDangerLevel) .ThenBy(p => p.posDangerCount) .ThenBy(p => p.distanceToMouse); if (sortedPosTable.First().posDangerCount != 0) //if can't dodge smoothly, dodge fast { var sortedPosTableFastest = posTable.OrderBy(p => p.isDangerousPos) .ThenByDescending(p => p.intersectionTime) .ThenBy(p => p.posDangerLevel) .ThenBy(p => p.posDangerCount); if (sortedPosTableFastest.First().posDangerCount == 0) { sortedPosTable = sortedPosTableFastest; fastEvadeMode = true; } } } foreach (var posInfo in sortedPosTable) { if (CheckPathCollision(myHero, posInfo.position) == false) { if (fastEvadeMode) { posInfo.position = GetExtendedSafePosition(ObjectCache.myHeroCache.serverPos2D, posInfo.position, extraEvadeDistance); return(CanHeroWalkToPos(posInfo.position, ObjectCache.myHeroCache.moveSpeed, ObjectCache.gamePing, 0)); } if (PositionInfoStillValid(posInfo)) { if (posInfo.position.CheckDangerousPos(extraEvadeDistance)) //extra evade distance, no multiple skillshots { posInfo.position = GetExtendedSafePosition(ObjectCache.myHeroCache.serverPos2D, posInfo.position, extraEvadeDistance); } return(posInfo); } } } return(PositionInfo.SetAllUndodgeable()); }