225 lines
6.7 KiB
Lua
225 lines
6.7 KiB
Lua
-- InnerFireWatch (Turtle WoW / 1.12.1)
|
|
-- Tracks key self-buffs and alerts when they fall off:
|
|
-- - Priest: Inner Fire
|
|
-- - Warrior: Battle Shout
|
|
-- - Shaman: Lightning Shield / Water Shield / Earth Shield
|
|
|
|
InnerFireWatchDB = InnerFireWatchDB or {}
|
|
|
|
local f = CreateFrame("Frame")
|
|
|
|
local DEFAULTS = {
|
|
enabled = true,
|
|
soundEnabled = true,
|
|
gainedMessage = false,
|
|
largeMessageEnabled = true,
|
|
|
|
useCustomSound = true,
|
|
customSoundPath = "Interface\\AddOns\\InnerFireWatch\\sounds\\expire.wav",
|
|
fallbackSound = "igQuestFailed",
|
|
}
|
|
|
|
local function ApplyDefaults()
|
|
for k, v in pairs(DEFAULTS) do
|
|
if InnerFireWatchDB[k] == nil then
|
|
InnerFireWatchDB[k] = v
|
|
end
|
|
end
|
|
end
|
|
|
|
-- Big center-screen text (independent of UIErrorsFrame)
|
|
local CenterAlert = CreateFrame("Frame", "InnerFireWatchCenterAlert", UIParent)
|
|
CenterAlert:SetPoint("CENTER", UIParent, "CENTER", 0, 120)
|
|
CenterAlert:SetWidth(600)
|
|
CenterAlert:SetHeight(80)
|
|
CenterAlert:Hide()
|
|
|
|
CenterAlert.text = CenterAlert:CreateFontString(nil, "OVERLAY")
|
|
CenterAlert.text:SetAllPoints(CenterAlert)
|
|
CenterAlert.text:SetFont("Fonts\\FRIZQT__.TTF", 32, "OUTLINE")
|
|
CenterAlert.text:SetJustifyH("CENTER")
|
|
CenterAlert.text:SetJustifyV("MIDDLE")
|
|
|
|
local function ShowCenterAlert(msg, r, g, b)
|
|
CenterAlert.text:SetText(msg or "")
|
|
CenterAlert.text:SetTextColor(r or 1, g or 0.1, b or 0.1)
|
|
CenterAlert:Show()
|
|
CenterAlert.startTime = GetTime()
|
|
end
|
|
|
|
-- Fade out over ~1.6s
|
|
CenterAlert:SetScript("OnUpdate", function()
|
|
if not CenterAlert:IsShown() then return end
|
|
local t = GetTime() - (CenterAlert.startTime or 0)
|
|
if t >= 1.6 then
|
|
CenterAlert:Hide()
|
|
return
|
|
end
|
|
local alpha = 1 - (t / 1.6)
|
|
CenterAlert:SetAlpha(alpha)
|
|
end)
|
|
|
|
-- Returns true if player currently has a buff whose texture contains textureNeedle (lowercase compare).
|
|
local function HasBuffByTexture(textureNeedle)
|
|
local i = 1
|
|
while true do
|
|
local texture = UnitBuff("player", i)
|
|
if not texture then break end
|
|
|
|
texture = string.lower(texture)
|
|
if string.find(texture, textureNeedle) then
|
|
return true
|
|
end
|
|
|
|
i = i + 1
|
|
end
|
|
return false
|
|
end
|
|
|
|
local function PlayExpireSound()
|
|
if not InnerFireWatchDB.soundEnabled then return end
|
|
|
|
if InnerFireWatchDB.useCustomSound and PlaySoundFile then
|
|
PlaySoundFile(InnerFireWatchDB.customSoundPath)
|
|
return
|
|
end
|
|
|
|
if PlaySound then
|
|
PlaySound(InnerFireWatchDB.fallbackSound)
|
|
end
|
|
end
|
|
|
|
local function NotifyExpired(buffLabel)
|
|
local msg = buffLabel .. " has expired!"
|
|
DEFAULT_CHAT_FRAME:AddMessage("|cffff3333" .. msg .. "|r")
|
|
|
|
if InnerFireWatchDB.largeMessageEnabled then
|
|
ShowCenterAlert(string.upper(buffLabel) .. " EXPIRED!")
|
|
end
|
|
|
|
if UIErrorsFrame and UIErrorsFrame.AddMessage then
|
|
UIErrorsFrame:AddMessage(msg, 1.0, 0.1, 0.1, 1.0, 5)
|
|
end
|
|
|
|
PlayExpireSound()
|
|
end
|
|
|
|
local function NotifyGained(buffLabel)
|
|
if not InnerFireWatchDB.gainedMessage then return end
|
|
DEFAULT_CHAT_FRAME:AddMessage("|cff33ff33" .. buffLabel .. " active.|r")
|
|
end
|
|
|
|
-- Build trackers based on class
|
|
local trackers = {}
|
|
local function BuildTrackers()
|
|
trackers = {}
|
|
|
|
local _, classToken = UnitClass("player")
|
|
if classToken == "PRIEST" then
|
|
table.insert(trackers, {
|
|
label = "Inner Fire",
|
|
needle = "spell_holy_innerfire",
|
|
active = false,
|
|
})
|
|
elseif classToken == "WARRIOR" then
|
|
table.insert(trackers, {
|
|
label = "Battle Shout",
|
|
needle = "ability_warrior_battleshout",
|
|
active = false,
|
|
})
|
|
elseif classToken == "SHAMAN" then
|
|
-- Texture needles are based on the icon file names.
|
|
-- Lightning Shield: Spell_Nature_LightningShield
|
|
-- Water Shield: Ability_Shaman_WaterShield
|
|
-- Earth Shield: Spell_Nature_SkinOfEarth (commonly used in TBC/clients that add it)
|
|
table.insert(trackers, { label = "Lightning Shield", needle = "spell_nature_lightningshield", active = false })
|
|
table.insert(trackers, { label = "Water Shield", needle = "ability_shaman_watershield", active = false })
|
|
table.insert(trackers, { label = "Earth Shield", needle = "spell_nature_skinofearth", active = false })
|
|
end
|
|
|
|
for _, t in ipairs(trackers) do
|
|
t.active = HasBuffByTexture(t.needle)
|
|
end
|
|
end
|
|
|
|
local function Check()
|
|
if not InnerFireWatchDB.enabled then return end
|
|
if not trackers or table.getn(trackers) == 0 then return end
|
|
|
|
for _, t in ipairs(trackers) do
|
|
local nowActive = HasBuffByTexture(t.needle)
|
|
|
|
if t.active and (not nowActive) then
|
|
NotifyExpired(t.label)
|
|
elseif (not t.active) and nowActive then
|
|
NotifyGained(t.label)
|
|
end
|
|
|
|
t.active = nowActive
|
|
end
|
|
end
|
|
|
|
f:RegisterEvent("PLAYER_LOGIN")
|
|
f:RegisterEvent("PLAYER_AURAS_CHANGED")
|
|
|
|
f:SetScript("OnEvent", function()
|
|
Check()
|
|
end)
|
|
|
|
-- Init after saved vars load
|
|
f:SetScript("OnUpdate", function()
|
|
f:SetScript("OnUpdate", nil)
|
|
ApplyDefaults()
|
|
BuildTrackers()
|
|
end)
|
|
|
|
-- Slash commands
|
|
SLASH_INNERFIREWATCH1 = "/ifw"
|
|
SlashCmdList["INNERFIREWATCH"] = function(msg)
|
|
msg = msg and string.lower(msg) or ""
|
|
|
|
if msg == "on" then
|
|
InnerFireWatchDB.enabled = true
|
|
DEFAULT_CHAT_FRAME:AddMessage("InnerFireWatch: enabled")
|
|
elseif msg == "off" then
|
|
InnerFireWatchDB.enabled = false
|
|
DEFAULT_CHAT_FRAME:AddMessage("InnerFireWatch: disabled")
|
|
|
|
elseif msg == "sound on" then
|
|
InnerFireWatchDB.soundEnabled = true
|
|
DEFAULT_CHAT_FRAME:AddMessage("InnerFireWatch: sound enabled")
|
|
elseif msg == "sound off" then
|
|
InnerFireWatchDB.soundEnabled = false
|
|
DEFAULT_CHAT_FRAME:AddMessage("InnerFireWatch: sound disabled")
|
|
|
|
elseif msg == "custom on" then
|
|
InnerFireWatchDB.useCustomSound = true
|
|
DEFAULT_CHAT_FRAME:AddMessage("InnerFireWatch: custom sound enabled")
|
|
elseif msg == "custom off" then
|
|
InnerFireWatchDB.useCustomSound = false
|
|
DEFAULT_CHAT_FRAME:AddMessage("InnerFireWatch: custom sound disabled")
|
|
|
|
elseif msg == "gained on" then
|
|
InnerFireWatchDB.gainedMessage = true
|
|
DEFAULT_CHAT_FRAME:AddMessage("InnerFireWatch: gained message enabled")
|
|
elseif msg == "gained off" then
|
|
InnerFireWatchDB.gainedMessage = false
|
|
DEFAULT_CHAT_FRAME:AddMessage("InnerFireWatch: gained message disabled")
|
|
|
|
elseif msg == "large on" then
|
|
InnerFireWatchDB.largeMessageEnabled = true
|
|
DEFAULT_CHAT_FRAME:AddMessage("InnerFireWatch: large message enabled")
|
|
elseif msg == "large off" then
|
|
InnerFireWatchDB.largeMessageEnabled = false
|
|
DEFAULT_CHAT_FRAME:AddMessage("InnerFireWatch: large message disabled")
|
|
|
|
else
|
|
DEFAULT_CHAT_FRAME:AddMessage("InnerFireWatch commands:")
|
|
DEFAULT_CHAT_FRAME:AddMessage(" /ifw on|off")
|
|
DEFAULT_CHAT_FRAME:AddMessage(" /ifw sound on|sound off")
|
|
DEFAULT_CHAT_FRAME:AddMessage(" /ifw custom on|custom off")
|
|
DEFAULT_CHAT_FRAME:AddMessage(" /ifw gained on|gained off")
|
|
DEFAULT_CHAT_FRAME:AddMessage(" /ifw large on|large off")
|
|
end
|
|
end
|