Created
April 17, 2017 21:14
-
-
Save StinkyTwitch/cd614e80ac9593f61d2ac57ec55b8926 to your computer and use it in GitHub Desktop.
OLD FH Warlock Destro PvP
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
-- Firehack script for destruction warlocks | |
-- Created: 7/21/2016 | |
-- Constants | |
UPDATE_INTERVAL = 0.1 -- in seconds | |
LAST_UPDATE = GetTime() | |
InitFrame = CreateFrame("Frame") | |
InitFrame:SetScript("OnUpdate", InitFrameUpdate) | |
print("Started Combat Routine") | |
function InitFrameUpdate(self, elapsed) | |
local t = GetTime() | |
if LAST_UPDATE + UPDATE_INTERVAL < t then | |
LAST_UPDATE = t | |
CombatRoutine() | |
end | |
end | |
-- The combat routine | |
function CombatRoutine() | |
--print("In CombatRoutine()") | |
-- If we are casting a spell, then exit | |
local spell, subtext, text, texture, startTime, endTime = UnitCastingInfo("player") | |
if spell then | |
-- Face our target | |
if not IsPlayerFacing("target") then FaceObject("target") end | |
return true | |
end | |
-- Handle buffs here, and GCD check via immolate | |
if HasFullControl() and CanCastSpell("Immolate") then | |
--print("Player has control") | |
-- Sacrifice minion | |
if not PlayerHasBuff("Demonic Power") then | |
--print("Sacrifice minion") | |
if HasPet() then | |
CastSpellByName("Grimoire of Sacrifice") | |
else | |
if GetSoulShards() >= 1 then CastSpellByName("Summon Felhunter") end | |
end | |
return true | |
end | |
-- Mana Tap or Life Tap, then exit | |
if InCombatLockdown() and not PlayerHasBuff("Mana Tap") then | |
if PlayerManaPercent() > 25.0 then | |
CastSpellByName("Mana Tap") | |
else | |
CastSpellByName("Life Tap") | |
end | |
return true | |
end | |
local hostilePlayers, hostilePlayersCount = GetHostilePlayersInRange(40) | |
local havocPlayer = PlayerDebuffExists(hostilePlayers, "Havoc") | |
-- Nobody to attack, return | |
if hostilePlayersCount == 0 then return true end | |
-- If there are 2 or more hostile players and no havocPlayer, throw havoc on one of them | |
if not havocPlayer and hostilePlayersCount > 1 then | |
-- Try to throw Havoc on the player with the least HP | |
havocPlayer = hostilePlayers[2] | |
print("Havoc on " .. GetUnitName(havocPlayer, true)) | |
print("Attacking " .. GetUnitName(hostilePlayers[1], true)) | |
TargetUnit(havocPlayer) | |
CastSpellByName("Havoc") | |
TargetUnit(hostilePlayers[1]) | |
return true | |
end | |
-- remove a target if it goes out of range | |
if GetDistanceBetweenObjects("player", "target") > 40 or UnitIsDead("target") or not InLOS("player", "target") then | |
print("Removing target") | |
ClearTarget() | |
end | |
-- Find a target | |
if not GetUnitName("target") then | |
-- No target, so target somebody | |
if hostilePlayersCount == 1 then | |
TargetUnit(hostilePlayer[1]) | |
elseif hostilePlayersCount > 1 then | |
if ObjectHasDebuff(hostilePlayer[1], "Havoc") then | |
-- target 1 has Havoc, so attack 2 | |
TargetUnit(hostilePlayer[2]) | |
print("New target " .. GetUnitName(hostilePlayer[2])) | |
else | |
TargetUnit(hostilePlayer[1]) | |
print("New target " .. GetUnitName(hostilePlayer[1])) | |
end | |
end | |
end | |
if not UnitIsEnemy("player", "target") then return end | |
-- Cast immolate if targets health is above 50% | |
if TargetHealthPercent() >= 50 and not ObjectHasDebuff("target", "Immolate") then | |
if not IsPlayerFacing("target") then FaceObject("target") end | |
CastSpellByName("Immolate") | |
--print ("Immolate") | |
return true | |
end | |
local soulShards = GetSoulShards() | |
-- Cast conflagrate if we have less than 5 shards | |
if soulShards < 5 and CanCastSpell("Conflagrate") then | |
if not IsPlayerFacing("target") then FaceObject("target") end | |
CastSpellByName("Conflagrate") | |
--print ("Conflagrate") | |
return true | |
end | |
-- Cast Shadowburn if we have more than 0 shards | |
if soulShards >= 1 then | |
if not IsPlayerFacing("target") then FaceObject("target") end | |
CastSpellByName("Shadowburn") | |
--print ("Shadowburn") | |
return true | |
end | |
--print ("Filler") | |
-- We have nothing to cast, so cast Immolate on nearby targets | |
target = GetUnitName("target", true) | |
for i, obj in pairs(hostilePlayers) do | |
if not ObjectHasDebuff(obj, "Immolate") then | |
if not IsPlayerFacing("target") then FaceObject("target") end | |
TargetUnit(obj) | |
CastSpellByName("Immolate") | |
TargetUnit(target) | |
return true | |
end | |
end | |
-- We wont be casting immolate on nearby targets here, so cast incinerate | |
if not IsPlayerFacing("target") then FaceObject("target") end | |
CastSpellByName("Incinerate") | |
end | |
end | |
-- Get a list of hostile player objects both in range and los | |
-- sorted by their health ascending, i.e. index 1 has less hp than index 2 | |
function GetHostilePlayersInRange(range) | |
hostilePlayers = {} | |
count = 0 | |
for i = 1, GetObjectCount() do | |
local obj = GetObjectWithIndex(i) | |
-- check if the object is an enemy player | |
if ObjectIsType(obj, ObjectTypes.Player) and UnitIsEnemy("player", obj) and not UnitIsDeadOrGhost(obj) and InLOS("player", obj) then | |
-- check if the object is in range | |
if GetDistanceBetweenObjects("player", obj) <= range then | |
hostilePlayers[#hostilePlayers + 1] = obj | |
count = count + 1 | |
end | |
end | |
end | |
table.sort(hostilePlayers, function(a, b) | |
return UnitHealth(a) < UnitHealth(b) | |
end) | |
return hostilePlayers, count | |
end | |
-- Check if obj has the debuff from the player | |
function ObjectHasDebuff(obj, debuff) | |
local name, rank, icon, count, debuffType, duration, expirationTime, unitCaster, isStealable, shouldConsolidate, spellId = UnitDebuff(obj, debuff) | |
if name and unitCaster == "player" then | |
return true | |
end | |
return false | |
end | |
-- Checks if any hostilePlayer has a debuff cast by the player | |
-- returns nil if it does not exist, returns the object with the debuff if it does exist | |
function PlayerDebuffExists(hostilePlayers, debuff) | |
for i, obj in pairs(hostilePlayers) do | |
local name, rank, icon, count, debuffType, duration, expirationTime, unitCaster, isStealable, shouldConsolidate, spellId = UnitDebuff(obj, debuff) | |
if name and unitCaster == "player" then | |
return obj | |
end | |
end | |
return nil | |
end | |
-- Checks if the player buff is active | |
function PlayerHasBuff(buff) | |
local name = UnitBuff("player", buff) | |
if name == buff then | |
return true | |
end | |
return false | |
end | |
-- Checks if the player can cast a spell (gcd, cooldown, etc) | |
-- check a spell like immolate for a gcd check | |
function CanCastSpell(spellName) | |
return (select(2, GetSpellCooldown(spellName)) == 0) | |
end | |
-- Checks if the players pet is summoned | |
function HasPet() | |
return (GetUnitName("pet") ~= nil) | |
end | |
-- Get soul shard count | |
function GetSoulShards() | |
return UnitPower("player", 7) | |
end | |
-- Check if player has control | |
function PlayerHasControl() | |
return (HasFullControl() == 1) | |
end | |
-- Get player mana percent | |
function PlayerManaPercent() | |
return (UnitMana("player") / UnitManaMax("player") * 100) | |
end | |
-- Get target health percent | |
function TargetHealthPercent() | |
return (UnitHealth("target") / UnitHealthMax("target") * 100) | |
end | |
-- Check line of sight | |
function InLOS(obj1, obj2) | |
local x1, y1, z1 = ObjectPosition(obj1) | |
local x2, y2, z2 = ObjectPosition(obj2) | |
if not TraceLine(x1, y1, z1+2.25, x2, y2, z2+2.25, bit.bor(0x10, 0x100)) then | |
return true | |
end | |
return false | |
end | |
-- Check facing | |
function IsPlayerFacing(obj) | |
local x1, y1, _ = ObjectPosition("player") | |
local x2, y2, _ = ObjectPosition(obj) | |
local playerFacing = ObjectFacing("player") | |
local deltaAngle = atan2(y1 - y2, x1 - x2) - deg(playerFacing) | |
if deltaAngle < 0 then | |
deltaAangle = deltaAngle + 360 | |
end | |
if deltaAngle > 120 and deltaAngle < 240 then | |
return true | |
end | |
return false | |
end | |
-- Face object | |
function FaceObject(obj) | |
local x1, y1, z1 = ObjectPosition("player") | |
local x2, y2, z2 = ObjectPosition(obj) | |
local angle = rad(atan2(y2 - y1, x2 - x1)) | |
if angle < 0 then | |
local angleFace = rad(atan2(y2 - y1, x2 - x1) + 360) | |
FaceDirection(angleFace) | |
else | |
FaceDirection(angle) | |
end | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment