Files
coa-details/plugins/Details_Vanguard/Details_Vanguard.lua
T
Tercio b6d51315a5 - Plugin Vanguard: got full rewrite and now it is more easy to use.
- Plugin TimeAttack: fixed problem where sometimes required a reload to start a new time.
- Plugin Damage the Game!: fixed a problem where sometimes the time didn't started after level 2.
- Custom display 'Health Potion & Stone' now also track Healing Tonic.
- Custom display 'Damage Taken by Spell' now track more spells and also melee hits.
- Menus now uses 'Friz Quadrata TT' font as default, also added an option to change it on options panel -> miscellaneous.
- 'Switch to Current' feature now switches all windows which have this option enabled.
- The message telling to use '/details reinstall' now only shows if a problem happen during the addon load process.
- Segments Saved option now can be set to 25, up from 5.
- Attempt to fix the bug with the monk spell 'Storm, Earth, and Fire'.
- Fixed 'Icon Pick' panel.
- Fixed bug when reporting friendly fire through player detail window.
- Fixed bug with report window where sometimes it was reporting on a wrong channel.
2015-01-16 03:44:29 -02:00

663 lines
20 KiB
Lua

local AceLocale = LibStub ("AceLocale-3.0")
local Loc = AceLocale:GetLocale ("Details")
---------------------------------------------------------------------------------------------
local _GetTime = GetTime --> wow api local
local _UFC = UnitAffectingCombat --> wow api local
local _IsInRaid = IsInRaid --> wow api local
local _IsInGroup = IsInGroup --> wow api local
local _UnitName = UnitName --> wow api local
local _UnitGroupRolesAssigned = UnitGroupRolesAssigned --> wow api local
local _UnitHealth = UnitHealth --> wow api local
local _UnitHealthMax = UnitHealthMax --> wow api local
local _UnitIsPlayer = UnitIsPlayer --> wow api local
local _UnitClass = UnitClass --> wow api local
local _UnitDebuff = UnitDebuff --> wow api local
local UnitGetIncomingHeals = UnitGetIncomingHeals
local _unpack = unpack
local UnitGetTotalAbsorbs = UnitGetTotalAbsorbs
---------------------------------------------------------------------------------------------
local _cstr = string.format --> lua library local
local _table_insert = table.insert --> lua library local
local _table_remove = table.remove --> lua library local
local _ipairs = ipairs --> lua library local
local _pairs = pairs --> lua library local
local _math_floor = math.floor --> lua library local
local _math_abs = math.abs --> lua library local
local _math_min = math.min --> lua library local
local _table_sort = table.sort
---------------------------------------------------------------------------------------------
--> Create plugin Object
local Vanguard = _detalhes:NewPluginObject ("Details_Vanguard")
--> Main Frame
local VanguardFrame = Vanguard.Frame
Vanguard:SetPluginDescription ("Show debuffs on each tanks in the raid, also shows incoming heal and damage and the last hits you took.")
local function CreatePluginFrames (data)
--> localize details functions
Vanguard.GetSpec = Vanguard.GetSpec
Vanguard.class_specs_coords = Vanguard.class_specs_coords
local framework = Vanguard:GetFramework()
--> OnDetailsEvent Parser
function Vanguard:OnDetailsEvent (event, ...)
if (event == "HIDE") then --> plugin hidded, disabled
VanguardFrame:UnregisterEvent ("ROLE_CHANGED_INFORM")
VanguardFrame:UnregisterEvent ("GROUP_ROSTER_UPDATE")
VanguardFrame:UnregisterEvent ("PLAYER_TARGET_CHANGED")
Vanguard:CombatEnd()
elseif (event == "SHOW") then --> plugin shown, enabled
Vanguard.CurrentInstance = Vanguard:GetInstance (Vanguard.instance_id)
VanguardFrame:RegisterEvent ("ROLE_CHANGED_INFORM")
VanguardFrame:RegisterEvent ("GROUP_ROSTER_UPDATE")
VanguardFrame:RegisterEvent ("PLAYER_TARGET_CHANGED")
Vanguard:ResetBars()
--Vanguard:ResetDebuffs() -- ??
Vanguard:IdentifyTanks()
Vanguard.CurrentInstance = Vanguard:GetInstance (Vanguard.instance_id)
Vanguard.CurrentCombat = _detalhes:GetCombat ("current")
VanguardFrame:SetFrameStrata (Vanguard.CurrentInstance.baseframe:GetFrameStrata())
VanguardFrame:SetFrameLevel (Vanguard.CurrentInstance.baseframe:GetFrameLevel()+5)
if (Vanguard:IsInCombat()) then
Vanguard:CombatStart()
end
VanguardFrame:SetPoint ("topleft", Vanguard.CurrentInstance.baseframe, "topleft")
VanguardFrame:SetPoint ("bottomright", Vanguard.CurrentInstance.baseframe, "bottomright")
elseif (event == "COMBAT_PLAYER_ENTER") then --> a new combat has been started
Vanguard.CurrentInstance = Vanguard:GetInstance (Vanguard.instance_id)
Vanguard.CurrentCombat = select (1, ...)
Vanguard.Running = true
Vanguard:CombatStart()
elseif (event == "COMBAT_PLAYER_LEAVE") then --> current combat has finished
Vanguard.CurrentCombat = select (1, ...)
Vanguard:CombatEnd()
Vanguard:ResetBars()
Vanguard:ResetBlocks()
elseif (event == "GROUP_ONLEAVE") then
if (Vanguard.Running) then
Vanguard:CombatEnd()
Vanguard:ResetBars()
Vanguard:ResetBlocks()
end
Vanguard:IdentifyTanks()
elseif (event == "DETAILS_INSTANCE_ENDRESIZE" or event == "DETAILS_INSTANCE_SIZECHANGED") then
--Vanguard:OnResize()
elseif (event == "PLUGIN_DISABLED") then
elseif (event == "PLUGIN_ENABLED") then
end
end
-- não vamos mais mostrar o jogador
-- somente barra de inc heal + absorbs
-- somente barra de vida
-- option tank square size
--> list with tank names
Vanguard.TankList = {} --> tanks
Vanguard.TankHashNames = {} --> tanks
Vanguard.TankBlocks = {} --> tank frames
--> search for tanks in the raid or party group
function Vanguard:IdentifyTanks()
table.wipe (Vanguard.TankList)
table.wipe (Vanguard.TankHashNames)
if (IsInRaid()) then
for i = 1, GetNumGroupMembers(), 1 do
local role = _UnitGroupRolesAssigned ("raid" .. i)
if (role == "TANK") then
local name, realm = UnitName ("raid"..i)
if (realm) then
name = name .. "-" .. realm
end
Vanguard.TankList [#Vanguard.TankList+1] = name
Vanguard.TankHashNames [name] = #Vanguard.TankList
end
end
elseif (IsInGroup()) then
for i = 1, GetNumGroupMembers()-1, 1 do
local role = _UnitGroupRolesAssigned ("party"..i)
if (role == "TANK") then
local name, realm = UnitName ("party"..i)
if (realm) then
name = name .. "-" .. realm
end
Vanguard.TankList [#Vanguard.TankList+1] = name
Vanguard.TankHashNames [name] = #Vanguard.TankList
end
end
local role = _UnitGroupRolesAssigned ("player")
if (role == "TANK") then
local name, realm = UnitName ("player")
if (realm) then
name = name .. "-" .. realm
end
Vanguard.TankList [#Vanguard.TankList+1] = name
Vanguard.TankHashNames [name] = #Vanguard.TankList
end
else
local name, realm = UnitName ("player")
if (realm) then
name = name .. "-" .. realm
end
Vanguard.TankList [#Vanguard.TankList+1] = name
Vanguard.TankHashNames [name] = #Vanguard.TankList
end
Vanguard:RefreshTanks()
end
function Vanguard:ResetBars()
for i, tankblock in ipairs (Vanguard.TankBlocks) do
local bar = tankblock.heal_inc
bar:SetSplit (50)
bar:SetLeftText (tankblock.tankname_string)
bar:SetRightText ("")
bar:SetRightColor (.25, 0, 0, 1)
bar:SetLeftColor (0, .25, 0, 1)
end
end
function Vanguard:ResetBlocks()
for i, tblock in ipairs (Vanguard.TankBlocks) do
tblock.statusbar:SetValue (100)
tblock.debuffs_using = 0
tblock.debuffs_next_index = 1
for i = 1, 3 do
local dblock = tblock.debuffs_blocks [i]
dblock.texture:SetTexture (nil)
dblock.stack:SetText ("")
dblock.stack_bg:Hide()
dblock:SetCooldown (0, 0, 0, 0)
dblock.in_use = nil
dblock.support.spellid = nil
end
end
end
local SetTank = function (self, index)
local name = Vanguard.TankList [index]
self.tankname:SetText (Vanguard:GetOnlyName (name))
self.tankname_string = name
local bar = self.heal_inc
bar.tankname = name
local class, left, right, top, bottom, r, g, b = Vanguard:GetClass (name)
local spec = Vanguard:GetSpec (name)
if (spec) then
self.specicon:SetTexture (Vanguard.CurrentInstance.row_info.spec_file)
self.specicon:SetTexCoord (_unpack (Vanguard.class_specs_coords [spec]))
else
self.specicon:SetTexture (Vanguard.CurrentInstance.row_info.icon_file)
self.specicon:SetTexCoord (left, right, top, bottom)
end
self.texture:SetVertexColor (r, g, b)
bar.lefticon = Vanguard.CurrentInstance.row_info.icon_file
bar.iconleft:SetTexCoord (left, right, top, bottom)
bar:SetLeftText (Vanguard:GetOnlyName (name))
bar:SetLeftText (name)
end
local debuff_on_enter = function (self)
if (self.spellid) then
GameTooltip:SetOwner (self, "ANCHOR_TOPLEFT")
GameTooltip:SetSpellByID (self.spellid)
GameTooltip:Show()
end
end
local debuff_on_leave = function (self)
if (self.spellid) then
GameTooltip:Hide()
end
end
function Vanguard:CreateTankBlock (index)
--frame
local f = CreateFrame ("button", "VanguardTankBlock" .. index, VanguardFrame)
f.SetTank = SetTank
f:SetSize (150, 50)
f:SetPoint ("bottomleft", VanguardFrame, "bottomleft", 5 + ((index-1) * 155), 5)
f:SetBackdrop ({bgFile = [[Interface\AddOns\Details\images\background]], tile = true, tileSize = 16, insets = {left = 0, right = 0, top = 0, bottom = 0}, edgeFile = [[Interface\DialogFrame\UI-DialogBox-Border]], edgeSize = 10})
--statusbar
f.statusbar = CreateFrame ("statusbar", nil, f)
f.statusbar:SetPoint ("topleft", f, "topleft", 5, -5)
f.statusbar:SetPoint ("bottomright", f, "bottomright", -5, 5)
f.texture = f.statusbar:CreateTexture (nil, "artwork")
f.statusbar:SetStatusBarTexture (f.texture)
f.statusbar:SetMinMaxValues (0, 100)
f.statusbar:SetValue (100)
f.texture:SetTexture ([[Interface\AddOns\Details\images\bar_serenity]])
--spec icon
f.specicon = f.statusbar:CreateTexture (nil, "overlay")
f.specicon:SetPoint ("topleft", f, "topleft", 5, -5)
f.specicon:SetSize (14, 14)
--tank name
f.tankname = f.statusbar:CreateFontString (nil, "overlay", "GameFontNormal")
f.tankname:SetPoint ("left", f.specicon, "right", 2, 0)
--debuff icons
f.debufficons = {}
--inc heals inc damage
f.heal_inc = framework:NewSplitBar (VanguardFrame, VanguardFrame, "VanguardDamageVsHeal" .. index, "DamageVsHeal" .. index, 294, 14)
f.heal_inc:SetPoint ("topleft", VanguardFrame, "topleft", 3, -3 + ((index - 1) * -16))
f.heal_inc:SetPoint ("topright", VanguardFrame, "topright", -3, -3 + ((index - 1) * -16))
f.heal_inc.fontsize = 10
f.heal_inc.righticon = "Interface\\ICONS\\misc_arrowleft"
f.heal_inc.iconright:SetVertexColor (1, .5, .5, 1)
--debuffs blocks
f.debuffs_blocks = {}
f.debuffs_using = 0
f.debuffs_next_index = 1
for i = 1, 3 do
local support_frame = CreateFrame ("frame", nil, f)
support_frame:SetFrameLevel (f:GetFrameLevel()+1)
support_frame:SetSize (24, 24)
support_frame:SetPoint ("bottomleft", f, "bottomleft", 5 + ((i-1) * 35), 5)
support_frame:SetScript ("OnEnter", debuff_on_enter)
support_frame:SetScript ("OnLeave", debuff_on_leave)
local texture = support_frame:CreateTexture (nil, "overlay")
texture:SetSize (24, 24)
texture:SetPoint ("bottomleft", f, "bottomleft", 5 + ((i-1) * 35), 5)
local dblock = CreateFrame ("cooldown", "VanguardTankBlock" .. index.. "Cooldown" .. i, support_frame, "CooldownFrameTemplate")
dblock:SetPoint ("topleft", texture, "topleft")
dblock:SetPoint ("bottomright", texture, "bottomright")
dblock.texture = texture
local stack = dblock:CreateFontString (nil, "overlay", "GameFontNormal")
stack:SetPoint ("bottomright", dblock, "bottomright", 8, 0)
local stack_bg = dblock:CreateTexture (nil, "artwork")
stack_bg:SetTexture (0, 0, 0)
stack_bg:SetPoint ("bottomright", dblock, "bottomright", 8, 0)
stack_bg:SetSize (12, 12)
dblock.stack = stack
dblock.stack_bg = stack_bg
dblock.support = support_frame
f.debuffs_blocks [i] = dblock
end
Vanguard.TankBlocks [index] = f
return f
end
function Vanguard:RefreshTanks()
for i = 1, #Vanguard.TankList do
local block = Vanguard.TankBlocks [i]
if (not block) then
block = Vanguard:CreateTankBlock (i)
end
block:SetTank (i)
end
if (Vanguard.Running) then
Vanguard:CombatEnd()
Vanguard:CombatStart()
end
end
function Vanguard:TrackIncoming()
for tank_name, block_index in pairs (Vanguard.TankHashNames) do
local shields = UnitGetTotalAbsorbs (tank_name) or 0
local heals = UnitGetIncomingHeals (tank_name) or 0
local events_table = Vanguard.CurrentCombat.player_last_events [tank_name]
local taken = 0
if (events_table) then
for _, event in ipairs (events_table) do
if (event [1] and event [4]+5 > time()) then --> damage
taken = taken + event [3]
end
end
taken = taken / 3.5
end
local tframe = Vanguard.TankBlocks [block_index]
tframe.heal_inc:SetLeftText (Vanguard:ToK (shields + heals) .. " (|cFFFFFF55A: " .. Vanguard:ToK (shields) .. "|r)")
tframe.heal_inc:SetRightText (Vanguard:ToK ( _math_floor (taken)))
heals = heals + shields
if (taken > 0 and heals > 0) then
if (taken > heals) then
local p = heals / taken * 100
p = _math_abs (p - 100)
p = p / 2
p = p + 50
p = _math_abs (p - 100)
tframe.heal_inc:SetSplit (p)
else
local p = taken / heals * 100
p = _math_abs (p - 100)
p = p / 2
p = p + 50
tframe.heal_inc:SetSplit (p)
end
elseif (taken > 0) then
tframe.heal_inc:SetSplit (6)
elseif (heals > 0) then
tframe.heal_inc:SetSplit (94)
end
end
end
function Vanguard:CombatStart()
Vanguard.Running = true
VanguardFrame:RegisterEvent ("UNIT_HEALTH")
--Vanguard:TrackDebuffsAlreadyApplied()
VanguardFrame:RegisterEvent ("COMBAT_LOG_EVENT_UNFILTERED")
if (Vanguard.track_incoming) then
Vanguard:CancelTimer (Vanguard.track_incoming)
end
Vanguard.track_incoming = Vanguard:ScheduleRepeatingTimer ("TrackIncoming", 0.1)
end
function Vanguard:CombatEnd()
Vanguard.Running = false
VanguardFrame:UnregisterEvent ("UNIT_HEALTH")
VanguardFrame:UnregisterEvent ("COMBAT_LOG_EVENT_UNFILTERED")
if (Vanguard.track_incoming) then
Vanguard:CancelTimer (Vanguard.track_incoming)
end
end
function Vanguard:DebuffRefreshed (who_name, spellid)
local tank_index = Vanguard.TankHashNames [who_name]
--print ("On Refres tank index:", tank_index)
if (tank_index) then
local tframe = Vanguard.TankBlocks [tank_index]
--print ("Tank index OKE, tframe:", tframe)
for i = 1, 3 do
local dblock = tframe.debuffs_blocks [i]
if (dblock.support.spellid == spellid) then
--print ("REFRESH OKEY!")
local debuff_name = GetSpellInfo (spellid)
local _, _, icon, count, _, duration, expirationTime = _UnitDebuff (who_name, debuff_name)
dblock.texture:SetTexture (icon)
if (count and count > 0) then
dblock.stack:SetText (count)
dblock.stack_bg:Show()
else
dblock.stack:SetText ("")
dblock.stack_bg:Hide()
end
dblock:SetCooldown (GetTime(), expirationTime-GetTime(), 0, 0)
break
end
end
end
end
function Vanguard:DebuffRemoved (who_name, spellid)
local tank_index = Vanguard.TankHashNames [who_name]
if (tank_index) then
local tframe = Vanguard.TankBlocks [tank_index]
for i = 1, 3 do
local dblock = tframe.debuffs_blocks [i]
if (dblock.support.spellid == spellid) then
dblock.texture:SetTexture (nil)
dblock.stack:SetText ("")
dblock.stack_bg:Hide()
dblock:SetCooldown (0, 0, 0, 0)
dblock.in_use = nil
dblock.support.spellid = nil
for o = 1, 3 do
if (not tframe.debuffs_blocks [o].in_use) then
tframe.debuffs_next_index = o
break
end
end
tframe.debuffs_using = tframe.debuffs_using - 1
break
end
end
end
end
function Vanguard:DebuffApplied (who_name, spellid)
local tank_index = Vanguard.TankHashNames [who_name]
if (tank_index) then
local tframe = Vanguard.TankBlocks [tank_index]
if (tframe.debuffs_using < 3) then
local next_index = tframe.debuffs_next_index
if (next_index) then
local dblock = tframe.debuffs_blocks [next_index]
local debuff_name = GetSpellInfo (spellid)
local _, _, icon, count, _, duration, expirationTime = _UnitDebuff (who_name, debuff_name)
if (not icon) then
return
end
if (not duration) then
duration = 999
end
dblock.texture:SetTexture (icon)
if (count and count > 0) then
dblock.stack:SetText (count)
dblock.stack_bg:Show()
else
dblock.stack:SetText ("")
dblock.stack_bg:Hide()
end
dblock:SetCooldown (GetTime(), expirationTime-GetTime(), 0, 0)
dblock.in_use = true
dblock.support.spellid = spellid
for i = 1, 3 do
if (not tframe.debuffs_blocks [i].in_use) then
tframe.debuffs_next_index = i
break
end
end
end
end
end
end
function Vanguard:UpdateHealth (blockid)
local block = Vanguard.TankBlocks [blockid]
block.statusbar:SetValue (UnitHealth (block.tankname_string) / UnitHealthMax (block.tankname_string) * 100)
end
function Vanguard:HealthChanged (unitId)
local name, realm = UnitName (unitId)
if (realm) then
name = name .. "-" .. realm
end
local block = Vanguard.TankHashNames [name]
if (block) then
Vanguard:UpdateHealth (block)
end
end
end
local ignored_debuffs = {
[80354] = true, --temporal displacement
[57724] = true, --sated
[6788] = true, --weakened soul
[124275] = true, --light stagger
[124274] = true, --moderate stagger
}
function Vanguard:TrackDebuffsAlreadyApplied()
for tank_name, block_index in pairs (Vanguard.TankHashNames) do
for i = 1, 41 do
local _, _, icon, count, _, duration, expirationTime, unitCaster, _, _, spellid = _UnitDebuff (tank_name, i)
if (icon and spellid and not ignored_debuffs [spellid]) then
Vanguard:DebuffApplied (tank_name, spellid)
end
end
end
end
function Vanguard:OnEvent (_, event, arg1, token, time, who_serial, who_name, who_flags, _, alvo_serial, alvo_name, alvo_flags, _, spellid, spellname, spellschool, tipo)
if (event == "COMBAT_LOG_EVENT_UNFILTERED") then
if (token == "SPELL_AURA_APPLIED") then
if (Vanguard.TankHashNames [alvo_name] and tipo == "DEBUFF" and Vanguard.Running and not ignored_debuffs [spellid]) then
Vanguard:DebuffApplied (alvo_name, spellid)
end
elseif (token == "SPELL_AURA_REMOVED") then
if (Vanguard.TankHashNames [alvo_name] and tipo == "DEBUFF" and Vanguard.Running and not ignored_debuffs [spellid]) then
Vanguard:DebuffRemoved (alvo_name, spellid)
end
elseif (token == "SPELL_AURA_REFRESH") then
if (Vanguard.TankHashNames [alvo_name] and tipo == "DEBUFF" and Vanguard.Running and not ignored_debuffs [spellid]) then
Vanguard:DebuffRefreshed (alvo_name, spellid)
end
elseif (token == "SPELL_AURA_APPLIED_DOSE") then
if (Vanguard.TankHashNames [alvo_name] and tipo == "DEBUFF" and Vanguard.Running and not ignored_debuffs [spellid]) then
Vanguard:DebuffRefreshed (alvo_name, spellid)
end
elseif (token == "SPELL_AURA_REMOVED_DOSE") then
if (Vanguard.TankHashNames [alvo_name] and tipo == "DEBUFF" and Vanguard.Running and not ignored_debuffs [spellid]) then
Vanguard:DebuffRefreshed (alvo_name, spellid)
end
end
elseif (event == "UNIT_HEALTH") then
Vanguard:HealthChanged (arg1)
elseif (event == "ADDON_LOADED") then
local AddonName = arg1
if (AddonName == "Details_Vanguard") then
if (_G._detalhes) then
--> create widgets
CreatePluginFrames()
local MINIMAL_DETAILS_VERSION_REQUIRED = 1
local default_saved_table = {}
--> Install
local install, saveddata = _G._detalhes:InstallPlugin ("TANK", "Vanguard", "Interface\\Icons\\INV_Shield_77", Vanguard, "DETAILS_PLUGIN_VANGUARD", MINIMAL_DETAILS_VERSION_REQUIRED, "Details! Team", "v2.0", default_saved_table)
if (type (install) == "table" and install.error) then
print (install.error)
end
-- DETAILS_PLUGIN_VANGUARD.TankHashNames
--> Register needed events
_G._detalhes:RegisterEvent (Vanguard, "COMBAT_PLAYER_ENTER")
_G._detalhes:RegisterEvent (Vanguard, "COMBAT_PLAYER_LEAVE")
_G._detalhes:RegisterEvent (Vanguard, "DETAILS_INSTANCE_ENDRESIZE")
_G._detalhes:RegisterEvent (Vanguard, "DETAILS_INSTANCE_SIZECHANGED")
_G._detalhes:RegisterEvent (Vanguard, "GROUP_ONLEAVE")
VanguardFrame:RegisterEvent ("ZONE_CHANGED_NEW_AREA")
VanguardFrame:RegisterEvent ("PLAYER_ENTERING_WORLD")
end
end
elseif (event == "ROLE_CHANGED_INFORM" or event == "GROUP_ROSTER_UPDATE") then --> raid changes
if (Vanguard.CurrentInstance) then
Vanguard:IdentifyTanks()
end
elseif (event == "ZONE_CHANGED_NEW_AREA" or event == "PLAYER_ENTERING_WORLD") then --> logon or map changes
if (Vanguard.CurrentInstance) then
Vanguard:IdentifyTanks()
end
end
end