Script5


SUBMITTED BY: Alerand

DATE: May 3, 2016, 9:33 a.m.

FORMAT: Text only

SIZE: 21.4 kB

HITS: 20396

  1. --[[
  2. AutoCarry Plugin - Annie Hastur, the Dark Child 1.4.2 by Skeem
  3. With Code from Kain
  4. Copyright 2013
  5. Changelog :
  6. 1.0 - Initial Release
  7. 1.1 - Recoded Should Work Better
  8. - Fixed Auto Ignite
  9. - Fixed bug with ultimate
  10. - Fixed MEC no library required now
  11. - Added Draw Text now draws if target can die from combo
  12. - Added Auto Health Pots / Auto Mana Pots
  13. - Added Auto Zhonyas (Needs Work maybe set at 15% default)
  14. - Added Auto Spell Levels
  15. 1.2 - Added prodiction to W, R
  16. - W uses MEC
  17. 1.2.2 - Fixed bug with qFarm not deactivating
  18. - Fixed W & R.
  19. - Fixed Force Tibbers
  20. - Fixed Script not showing for some users
  21. 1.3 - Fixed W Usage (added new cone function)
  22. - Fixed recalling bug
  23. - Fixed Auto Pots
  24. 1.3.1 - Changed castR to vadash's
  25. 1.4 - Changed W Range
  26. - Fixed some issues with R
  27. - Added better support for revamped
  28. 1.4.1 - Added fix for casting W before R when stun is up
  29. 1.4.2 - Fixed spamming E while Recalling & Tweaked DFG Usage
  30. ]] --
  31. --[ Plugin Loads] --
  32. function PluginOnLoad()
  33. loadMain() -- Loads Global Variables
  34. menuMain() -- Loads AllClass Menu
  35. end
  36. --[/Loads]
  37. --[Plugin OnTick]--
  38. function PluginOnTick()
  39. if Recalling then return end -- If we're recalling then won't run any combos
  40. Checks()
  41. SmartKS()
  42. UseConsumables()
  43. if Menu.dAttack and Carry.AutoCarry then AutoCarry.CanAttack = false else AutoCarry.CanAttack = true end
  44. if not IsMyManaLow() and Menu.sFarm and Menu.qFarm and not HaveStun and not Carry.AutoCarry then qFarm()
  45. elseif not IsMyManaLow() and not Menu.sFarm and Menu.qFarm and not Carry.AutoCarry then qFarm() end
  46. if Menu.cStun and EREADY and not HaveStun then CastSpell(_E) end
  47. if Carry.AutoCarry then bCombo() end
  48. if Menu.sKS then SmartKS() end
  49. if Target and Carry.MixedMode then
  50. if Menu.qHarass and QREADY and GetDistance(Target) <= qRange then CastSpell(_Q, Target) end
  51. if Menu.wHarass and WREADY and GetDistance(Target) <= wRange then CastW(Target) end
  52. end
  53. if Extras.AutoLevelSkills then autoLevelSetSequence(levelSequence) end
  54. end
  55. --[/OnTick]--
  56. function qFarm()
  57. for _, minion in pairs(AutoCarry.EnemyMinions().objects) do
  58. local qDmg = getDmg("Q",minion,myHero)
  59. if ValidTarget(minion) and QREADY and GetDistance(minion) <= qRange then
  60. if qDmg >= minion.health then CastSpell(_Q, minion) end
  61. end
  62. end
  63. end
  64. --[Burst Combo Function]--
  65. function bCombo()
  66. if Target then
  67. if DFGREADY and GetDistance(Target) <= qRange then CastSpell(dfgSlot, Target) end
  68. if HXGREADY then CastSpell(hxgSlot, Target) end
  69. if BWCREADY then CastSpell(bwcSlot, Target) end
  70. if BRKREADY then CastSpell(brkSlot, Target) end
  71. if RREADY and GetDistance(Target) <= rRange and HaveStun then CastR(Target) end
  72. if EREADY and GetDistance(Target) <= wRange then CastSpell(_E) end
  73. if QREADY and GetDistance(Target) <= qRange then CastSpell(_Q, Target) end
  74. if WREADY and GetDistance(Target) <= wRange then CastW(Target) end
  75. end
  76. end
  77. --[/Burst Combo Function]--
  78. --[Skills that use MEC]--
  79. function CountEnemies(point, range)
  80. local ChampCount = 0
  81. for j = 1, heroManager.iCount, 1 do
  82. local enemyhero = heroManager:getHero(j)
  83. if myHero.team ~= enemyhero.team and ValidTarget(enemyhero, rRange+150) then
  84. if GetDistance(enemyhero, point) <= range then
  85. ChampCount = ChampCount + 1
  86. end
  87. end
  88. end
  89. return ChampCount
  90. end
  91. function CastR(Target)
  92. if RREADY then
  93. local ultPos = GetAoESpellPosition(450, Target, 250)
  94. if ultPos and GetDistance(ultPos) <= rRange then
  95. if CountEnemies(ultPos, 450) >= 1 then
  96. CastSpell(_R, ultPos.x, ultPos.z)
  97. end
  98. else
  99. if IsSACReborn and TS_GetPriority(Target) <= 2 then
  100. SkillR:Cast(Target)
  101. else
  102. CastSpell(_R, Target.x, Target.z)
  103. end
  104. end
  105. end
  106. end
  107. --[Skills that use MEC]--
  108. --[Casts our W Skill]--
  109. function CastW(enemy)
  110. if not enemy and ValidTarget(Target) then
  111. enemy = Target
  112. end
  113. if WREADY then
  114. if IsSACReborn then
  115. SkillW:Cast(enemy)
  116. else
  117. AutoCarry.CastSkillshot(SkillW, Target)
  118. end
  119. end
  120. end
  121. --[Smart KS Function]--
  122. function SmartKS()
  123. for i=1, heroManager.iCount do
  124. local enemy = heroManager:GetHero(i)
  125. if ValidTarget(enemy) then
  126. dfgDmg, hxgDmg, bwcDmg, iDmg = 0, 0, 0, 0
  127. qDmg = getDmg("Q",enemy,myHero)
  128. wDmg = getDmg("W",enemy,myHero)
  129. rDmg = getDmg("R",enemy,myHero)
  130. if DFGREADY then dfgDmg = (dfgSlot and getDmg("DFG",enemy,myHero) or 0) end
  131. if HXGREADY then hxgDmg = (hxgSlot and getDmg("HXG",enemy,myHero) or 0) end
  132. if BWCREADY then bwcDmg = (bwcSlot and getDmg("BWC",enemy,myHero) or 0) end
  133. if IREADY then iDmg = (ignite and getDmg("IGNITE",enemy,myHero) or 0) end
  134. onspellDmg = (liandrysSlot and getDmg("LIANDRYS",enemy,myHero) or 0)+(blackfireSlot and getDmg("BLACKFIRE",enemy,myHero) or 0)
  135. itemsDmg = dfgDmg + hxgDmg + bwcDmg + iDmg + onspellDmg
  136. if Menu.sKS then
  137. if enemy.health <= (qDmg) and GetDistance(enemy) <= qRange and QREADY then
  138. if QREADY then CastSpell(_Q, enemy) end
  139. elseif enemy.health <= (wDmg) and GetDistance(enemy) <= wRange and WREADY then
  140. if WREADY then CastW(enemy) end
  141. elseif enemy.health <= (qDmg + wDmg) and GetDistance(enemy) <= wRange and WREADY and QREADY then
  142. if QREADY then CastSpell(_Q, enemy) end
  143. if WREADY then CastW(enemy) end
  144. elseif enemy.health <= (qDmg + itemsDmg) and GetDistance(enemy) <= qRange and QREADY then
  145. if DFGREADY then CastSpell(dfgSlot, enemy) end
  146. if HXGREADY then CastSpell(hxgSlot, enemy) end
  147. if BWCREADY then CastSpell(bwcSlot, enemy) end
  148. if BRKREADY then CastSpell(brkSlot, enemy) end
  149. if QREADY then CastSpell(_Q, enemy) end
  150. elseif enemy.health <= (wDmg + itemsDmg) and GetDistance(enemy) <= wRange and WREADY then
  151. if DFGREADY then CastSpell(dfgSlot, enemy) end
  152. if HXGREADY then CastSpell(hxgSlot, enemy) end
  153. if BWCREADY then CastSpell(bwcSlot, enemy) end
  154. if BRKREADY then CastSpell(brkSlot, enemy) end
  155. if WREADY then CastW(enemy) end
  156. elseif enemy.health <= (qDmg + wDmg + itemsDmg) and GetDistance(enemy) <= wRange
  157. and WREADY and QREADY then
  158. if DFGREADY then CastSpell(dfgSlot, enemy) end
  159. if HXGREADY then CastSpell(hxgSlot, enemy) end
  160. if BWCREADY then CastSpell(bwcSlot, enemy) end
  161. if BRKREADY then CastSpell(brkSlot, enemy) end
  162. if WREADY and GetDistance(enemy) <= wRange then CastW(enemy) end
  163. if QREADY then CastSpell(_Q, enemy) end
  164. elseif enemy.health <= (qDmg + wDmg + rDmg + itemsDmg) and GetDistance(enemy) <= qRange
  165. and QREADY and EREADY and WREADY and RREADY and enemy.health > (qDmg + wDmg) then
  166. if DFGREADY then CastSpell(dfgSlot, enemy) end
  167. if HXGREADY then CastSpell(hxgSlot, enemy) end
  168. if BWCREADY then CastSpell(bwcSlot, enemy) end
  169. if BRKREADY then CastSpell(brkSlot, enemy) end
  170. if RREADY and GetDistance(enemy) <= rRange then CastR(enemy) end
  171. if QREADY and GetDistance(enemy) <= qRange then CastSpell(_Q, enemy) end
  172. if WREADY and GetDistance(enemy) <= wRange then CastW(enemy) end
  173. elseif enemy.health <= (rDmg + itemsDmg) and GetDistance(enemy) <= rRange
  174. and not QREADY and not EREADY and RREADY then
  175. if DFGREADY then CastSpell(dfgSlot, enemy) end
  176. if HXGREADY then CastSpell(hxgSlot, enemy) end
  177. if BWCREADY then CastSpell(bwcSlot, enemy) end
  178. if BRKREADY then CastSpell(brkSlot, enemy) end
  179. if RREADY then CastR(enemy) end
  180. end
  181. end
  182. KillText[i] = 1
  183. if enemy.health <= (qDmg + wDmg + itemsDmg) and QREADY and WREADY then
  184. KillText[i] = 2
  185. end
  186. if enemy.health <= (qDmg + wDmg + rDmg + itemsDmg) and QREADY and WREADY and RREADY then
  187. KillText[i] = 3
  188. end
  189. if enemy.health <= iDmg and GetDistance(enemy) <= 600 then
  190. if IREADY then CastSpell(ignite, enemy) end
  191. end
  192. end
  193. end
  194. end
  195. --[/Smart KS Function]--
  196. function UseConsumables()
  197. if not InFountain() and not Recalling and Target ~= nil then
  198. if Extras.aHP and myHero.health < (myHero.maxHealth * (Extras.HPHealth / 100))
  199. and not (usingHPot or usingFlask) and (hpReady or fskReady) then
  200. CastSpell((hpSlot or fskSlot))
  201. end
  202. if Extras.aMP and myHero.mana < (myHero.maxMana * (Extras.MinMana / 100))
  203. and not (usingMPot or usingFlask) and (mpReady or fskReady) then
  204. CastSpell((mpSlot or fskSlot))
  205. end
  206. end
  207. end
  208. --[Low Mana Function by Kain]--
  209. function IsMyManaLow()
  210. if myHero.mana < (myHero.maxMana * ( Extras.MinMana / 100)) then
  211. return true
  212. else
  213. return false
  214. end
  215. end
  216. --[/Low Mana Function by Kain]--
  217. --[Low Health Function Trololz]--
  218. function IsMyHealthLow()
  219. if myHero.health < (myHero.maxHealth * ( Extras.ZWHealth / 100)) then
  220. return true
  221. else
  222. return false
  223. end
  224. end
  225. --[/Low Health Function Trololz]--
  226. --[Health Pots Function]--
  227. function NeedHP()
  228. if myHero.health < (myHero.maxHealth * ( Extras.HPHealth / 100)) then
  229. return true
  230. else
  231. return false
  232. end
  233. end
  234. --[Object Detection]--
  235. function PluginOnCreateObj(obj)
  236. if obj and GetDistance(obj) <= 50 then
  237. if obj.name == "StunReady.troy" then HaveStun = true end
  238. if obj.name == "BearFire_foot.troy" then HaveTibbers = true end
  239. if obj.name == "TeleportHome.troy" then Recall = true end
  240. end
  241. if obj.name:find("Global_Item_HealthPotion.troy") then
  242. if GetDistance(obj, myHero) <= 70 then
  243. usingHPot = true
  244. usingFlask = true
  245. end
  246. end
  247. if obj.name:find("Global_Item_ManaPotion.troy") then
  248. if GetDistance(obj, myHero) <= 70 then
  249. usingFlask = true
  250. usingMPot = true
  251. end
  252. end
  253. end
  254. function PluginOnDeleteObj(obj)
  255. if obj and GetDistance(obj) <= 50 then
  256. if obj.name == "StunReady.troy" then HaveStun = false end
  257. if obj.name == "BearFire_foot.troy" then HaveTibbers = false end
  258. if obj.name == "TeleportHome.troy" then Recall = false end
  259. end
  260. if obj.name:find("Global_Item_HealthPotion.troy") then
  261. if GetDistance(obj) <= 70 then
  262. usingHPot = false
  263. usingFlask = false
  264. end
  265. end
  266. if obj.name:find("Global_Item_ManaPotion.troy") then
  267. if GetDistance(obj) <= 70 then
  268. usingMPot = false
  269. usingFlask = false
  270. end
  271. end
  272. end
  273. --[/Object Detection]--
  274. -- Recalling Functions --
  275. function OnRecall(hero, channelTimeInMs)
  276. if hero.networkID == player.networkID then
  277. Recalling = true
  278. end
  279. end
  280. function OnAbortRecall(hero)
  281. if hero.networkID == player.networkID then
  282. Recalling = false
  283. end
  284. end
  285. function OnFinishRecall(hero)
  286. if hero.networkID == player.networkID then
  287. Recalling = false
  288. end
  289. end
  290. function PluginOnDraw()
  291. --> Ranges
  292. if not myHero.dead then
  293. if QREADY and Menu.qDraw then
  294. DrawCircle(myHero.x, myHero.y, myHero.z, qRange, 0x191970)
  295. end
  296. if Target and Menu.DrawTarget then
  297. DrawText("Targetting: " .. Target.charName, 15, 100, 100, 0xFFFF0000)
  298. end
  299. if Menu.cDraw then
  300. for i=1, heroManager.iCount do
  301. local Unit = heroManager:GetHero(i)
  302. if ValidTarget(Unit) then
  303. if waittxt[i] == 1 and (KillText[i] ~= nil or 0 or 1) then
  304. PrintFloatText(Unit, 0, TextList[KillText[i]])
  305. end
  306. end
  307. if waittxt[i] == 1 then
  308. waittxt[i] = 30
  309. else
  310. waittxt[i] = waittxt[i]-1
  311. end
  312. end
  313. end
  314. end
  315. end
  316. function loadMain()
  317. if AutoCarry.Skills then IsSACReborn = true else IsSACReborn = false end
  318. if IsSACReborn then AutoCarry.Skills:DisableAll() end
  319. Menu = AutoCarry.PluginMenu
  320. Carry = AutoCarry.MainMenu
  321. if IsSACReborn then
  322. AutoCarry.Crosshair:SetSkillCrosshairRange(630)
  323. else
  324. AutoCarry.SkillsCrosshair.range = 630
  325. end
  326. HaveStun, HaveTibbers, Recall = false, false, false
  327. hpReady, mpReady, fskReady = false, false, false
  328. HK1, HK2, HK3 = string.byte("Z"), string.byte("K"), string.byte("T")
  329. qRange, wRange, eRange, rRange = 625, 600, 600, 630
  330. TextList = {"Harass him!!", "Q+W KILL!!", "FULL COMBO KILL!"}
  331. KillText = {}
  332. waittxt = {} -- prevents UI lags, all credits to Dekaron
  333. for i=1, heroManager.iCount do waittxt[i] = i*3 end -- All credits to Dekaron
  334. levelSequence = { nil, 0, 1, 3, 1, 4, 1, 2, 1, 2, 4, 2, 2, 3, 3, 4, 3, 3, }
  335. if IsSACReborn then
  336. SkillW = AutoCarry.Skills:NewSkill(false, _W, wRange, "Incinerate", AutoCarry.SPELL_CONE, 0, false, false, 1.5, 650, 45, false)
  337. SkillR = AutoCarry.Skills:NewSkill(false, _R, rRange, "Infernal Guardian", AutoCarry.SPELL_CIRCLE, 0, false, false, 1.5, 250, 450, false)
  338. else
  339. SkillW = {spellKey = _W, range = wRange, speed = 1.5, delay = 250, width = 100, configName = "Incinerate", displayName = "W Incinerate", enabled = true, skillShot = true, minions = false, reset = false, reqTarget = false }
  340. SkillR = {spellKey = _R, range = rRange, speed = 1.5, delay = 250, width = 450, configName = "Incinerate", displayName = "W Incinerate", enabled = true, skillShot = true, minions = false, reset = false, reqTarget = false }
  341. end
  342. end
  343. function menuMain()
  344. Menu:addParam("sep", "-- Farm Options --", SCRIPT_PARAM_INFO, "")
  345. Menu:addParam("qFarm", "Disintegrate(Q) - Farm ", SCRIPT_PARAM_ONKEYTOGGLE, false, HK1)
  346. Menu:addParam("sFarm", "Don't Q Farm if Stun Ready", SCRIPT_PARAM_ONKEYTOGGLE, false, HK2)
  347. Menu:addParam("sep1", "-- Combo Options --", SCRIPT_PARAM_INFO, "")
  348. Menu:addParam("dAttack", "Disable Auto Attacks", SCRIPT_PARAM_ONKEYTOGGLE, false, HK3)
  349. Menu:addParam("cStun", "Charge Stun with E", SCRIPT_PARAM_ONOFF, true)
  350. Menu:addParam("fTibbers", "Force Tibbers without Stun", SCRIPT_PARAM_ONOFF, false)
  351. Menu:addParam("sep2", "-- Mixed Mode Options --", SCRIPT_PARAM_INFO, "")
  352. Menu:addParam("qHarass", "Use Disintegrate(Q)", SCRIPT_PARAM_ONOFF, true)
  353. Menu:addParam("wHarass", "Use Incinerate(W)", SCRIPT_PARAM_ONOFF, false)
  354. Menu:addParam("sep3", "-- KS Options --", SCRIPT_PARAM_INFO, "")
  355. Menu:addParam("sKS", "Use Smart Combo KS", SCRIPT_PARAM_ONOFF, true)
  356. Menu:addParam("sep5", "-- Draw Options --", SCRIPT_PARAM_INFO, "")
  357. Menu:addParam("qDraw", "Draw Disintegrate (Q)", SCRIPT_PARAM_ONOFF, true)
  358. Menu:addParam("DrawTarget", "Draw Target", SCRIPT_PARAM_ONOFF, true)
  359. Menu:addParam("cDraw", "Draw Enemy Text", SCRIPT_PARAM_ONOFF, true)
  360. Extras = scriptConfig("Sida's Auto Carry Plugin: "..myHero.charName..": Extras", myHero.charName)
  361. Extras:addParam("sep6", "-- Misc --", SCRIPT_PARAM_INFO, "")
  362. Extras:addParam("MinMana", "Minimum Mana for Q Farm %", SCRIPT_PARAM_SLICE, 40, 0, 100, 2)
  363. Extras:addParam("ZWItems", "Auto Zhonyas/Wooglets", SCRIPT_PARAM_ONOFF, true)
  364. Extras:addParam("ZWHealth", "Min Health % for Zhonyas/Wooglets", SCRIPT_PARAM_SLICE, 15, 0, 100, 2)
  365. Extras:addParam("aHP", "Auto Health Pots", SCRIPT_PARAM_ONOFF, true)
  366. Extras:addParam("aMP", "Auto Auto Mana Pots", SCRIPT_PARAM_ONOFF, true)
  367. Extras:addParam("HPHealth", "Min % for Health Pots", SCRIPT_PARAM_SLICE, 50, 0, 100, 2)
  368. Extras:addParam("AutoLevelSkills", "Auto Level Skills (Requires Reload)", SCRIPT_PARAM_ONOFF, true)
  369. end
  370. function Checks()
  371. if myHero:GetSpellData(SUMMONER_1).name:find("SummonerDot") then ignite = SUMMONER_1
  372. elseif myHero:GetSpellData(SUMMONER_2).name:find("SummonerDot") then ignite = SUMMONER_2 end
  373. if IsSACReborn then Target = AutoCarry.Crosshair:GetTarget(true) else Target = AutoCarry.GetAttackTarget(true) end
  374. dfgSlot, hxgSlot, bwcSlot = GetInventorySlotItem(3128), GetInventorySlotItem(3146), GetInventorySlotItem(3144)
  375. brkSlot = GetInventorySlotItem(3092),GetInventorySlotItem(3143),GetInventorySlotItem(3153)
  376. znaSlot, wgtSlot = GetInventorySlotItem(3157),GetInventorySlotItem(3090)
  377. hpSlot, mpSlot, fskSlot = GetInventorySlotItem(2003),GetInventorySlotItem(2004),GetInventorySlotItem(2041)
  378. QREADY = (myHero:CanUseSpell(_Q) == READY)
  379. WREADY = (myHero:CanUseSpell(_W) == READY)
  380. EREADY = (myHero:CanUseSpell(_E) == READY)
  381. RREADY = (myHero:CanUseSpell(_R) == READY and not HaveTibbers)
  382. DFGREADY = (dfgSlot ~= nil and myHero:CanUseSpell(dfgSlot) == READY)
  383. HXGREADY = (hxgSlot ~= nil and myHero:CanUseSpell(hxgSlot) == READY)
  384. BWCREADY = (bwcSlot ~= nil and myHero:CanUseSpell(bwcSlot) == READY)
  385. BRKREADY = (brkSlot ~= nil and myHero:CanUseSpell(brkSlot) == READY)
  386. ZNAREADY = (znaSlot ~= nil and myHero:CanUseSpell(znaSlot) == READY)
  387. WGTREADY = (wgtSlot ~= nil and myHero:CanUseSpell(wgtSlot) == READY)
  388. IREADY = (ignite ~= nil and myHero:CanUseSpell(ignite) == READY)
  389. hpReady = (hpSlot ~= nil and myHero:CanUseSpell(hpSlot) == READY)
  390. mpReady =(mpSlot ~= nil and myHero:CanUseSpell(mpSlot) == READY)
  391. fskReady = (fskSlot ~= nil and myHero:CanUseSpell(fskSlot) == READY)
  392. end
  393. --[[
  394. AoE_Skillshot_Position 2.0 by monogato
  395. GetAoESpellPosition(radius, main_target, [delay]) returns best position in order to catch as many enemies as possible with your AoE skillshot, making sure you get the main target.
  396. Note: You can optionally add delay in ms for prediction (VIP if avaliable, normal else).
  397. ]]
  398. function GetCenter(points)
  399. local sum_x = 0
  400. local sum_z = 0
  401. for i = 1, #points do
  402. sum_x = sum_x + points[i].x
  403. sum_z = sum_z + points[i].z
  404. end
  405. local center = {x = sum_x / #points, y = 0, z = sum_z / #points}
  406. return center
  407. end
  408. function ContainsThemAll(circle, points)
  409. local radius_sqr = circle.radius*circle.radius
  410. local contains_them_all = true
  411. local i = 1
  412. while contains_them_all and i <= #points do
  413. contains_them_all = GetDistanceSqr(points[i], circle.center) <= radius_sqr
  414. i = i + 1
  415. end
  416. return contains_them_all
  417. end
  418. -- The first element (which is gonna be main_target) is untouchable.
  419. function FarthestFromPositionIndex(points, position)
  420. local index = 2
  421. local actual_dist_sqr
  422. local max_dist_sqr = GetDistanceSqr(points[index], position)
  423. for i = 3, #points do
  424. actual_dist_sqr = GetDistanceSqr(points[i], position)
  425. if actual_dist_sqr > max_dist_sqr then
  426. index = i
  427. max_dist_sqr = actual_dist_sqr
  428. end
  429. end
  430. return index
  431. end
  432. function RemoveWorst(targets, position)
  433. local worst_target = FarthestFromPositionIndex(targets, position)
  434. table.remove(targets, worst_target)
  435. return targets
  436. end
  437. function GetInitialTargets(radius, main_target)
  438. local targets = {main_target}
  439. local diameter_sqr = 4 * radius * radius
  440. for i=1, heroManager.iCount do
  441. target = heroManager:GetHero(i)
  442. if target.networkID ~= main_target.networkID and ValidTarget(target) and GetDistanceSqr(main_target, target) < diameter_sqr then table.insert(targets, target) end
  443. end
  444. return targets
  445. end
  446. function GetPredictedInitialTargets(radius, main_target, delay)
  447. if VIP_USER and not vip_target_predictor then vip_target_predictor = TargetPredictionVIP(nil, nil, delay/1000) end
  448. local predicted_main_target = VIP_USER and vip_target_predictor:GetPrediction(main_target) or GetPredictionPos(main_target, delay)
  449. local predicted_targets = {predicted_main_target}
  450. local diameter_sqr = 4 * radius * radius
  451. for i=1, heroManager.iCount do
  452. target = heroManager:GetHero(i)
  453. if ValidTarget(target) then
  454. predicted_target = VIP_USER and vip_target_predictor:GetPrediction(target) or GetPredictionPos(target, delay)
  455. if target.networkID ~= main_target.networkID and GetDistanceSqr(predicted_main_target, predicted_target) < diameter_sqr then table.insert(predicted_targets, predicted_target) end
  456. end
  457. end
  458. return predicted_targets
  459. end
  460. -- I don't need range since main_target is gonna be close enough. You can add it if you do.
  461. function GetAoESpellPosition(radius, main_target, delay)
  462. local targets = delay and GetPredictedInitialTargets(radius, main_target, delay) or GetInitialTargets(radius, main_target)
  463. local position = GetCenter(targets)
  464. local best_pos_found = true
  465. local circle = Circle(position, radius)
  466. circle.center = position
  467. if #targets > 2 then best_pos_found = ContainsThemAll(circle, targets) end
  468. while not best_pos_found do
  469. targets = RemoveWorst(targets, position)
  470. position = GetCenter(targets)
  471. circle.center = position
  472. best_pos_found = ContainsThemAll(circle, targets)
  473. end
  474. return position, #targets
  475. end

comments powered by Disqus