diff --git a/Elements/armor.lua b/Elements/armor.lua new file mode 100644 index 0000000..b113908 --- /dev/null +++ b/Elements/armor.lua @@ -0,0 +1,161 @@ +--[[ SLDataText Module: Armor ]] +--[[ Author: Taffu RevDate: 07/13/2012 Version: 5.0.0 ]] + +-- Added guild fund repair + +local SLDT, MODNAME = SLDataText, "Armor" +if ( SLDT ) then SLDT.Armor = CreateFrame("Frame") end +local L = SLDT.Locale +local db, frame, text, tool + +local durMin, durCol +local function convertMoney(moolah, display) + local g, s, c = abs(moolah/10000), abs(mod(moolah/100, 100)), abs(mod(moolah, 100)) + local cash + if ( display ) then -- True = Long display + if ( g < 1 ) then g = "" else g = string.format("%d|cffffd700g|r ", g) end + if ( s < 1 ) then s = "" else s = string.format("%d|cffc7c7cfs|r ", s) end + c = string.format("%d|cffeda55fc|r", c) + cash = string.format("%s%s%s", g, s, c) + else + cash = string.format("%.1f|cffffd700g|r", g) + end + return cash +end + +local function SetupToolTip() + tool:SetScript("OnEnter", function(this) + GameTooltip:SetOwner(this, db.aF) + GameTooltip:AddLine("|cffffffff"..L["Armor"].."|r") + local durFull = true + for slot, slotName in gmatch("1HEAD3SHOULDER5CHEST6WAIST7LEGS8FEET9WRIST10HANDS16MAINHAND17SECONDARYHAND18RANGED","(%d+)([^%d]+)") do + local durCur, durMax = GetInventoryItemDurability(slot) + local slotName = _G[slotName.."SLOT"] + if ( durCur ~= durMax ) then + GameTooltip:AddDoubleLine(slotName, string.format("%.0f%%", durCur ~= 0 and durCur*(100/durMax) or 0), 1,1,0,1,1,1) + if ( durFull ) then durFull = false end + end + end + if ( durFull ) then + GameTooltip:AddDoubleLine(L["All Items"], "100%", 1,1,0,1,1,1) + end + GameTooltip:AddLine(" ") + GameTooltip:AddDoubleLine(L["Auto Repair"], string.format("%s", db.autorepair and L["On"] or L["Off"]), 1,1,0,1,1,1) + GameTooltip:Show() + end) + tool:SetScript("OnLeave", function(this) if ( GameTooltip:IsShown() ) then GameTooltip:Hide() end end) +end + +function SLDT.Armor:Enable() + if ( db.enabled ) then + SLDT:UpdateBaseText(self, db) + self:RegisterEvent("UPDATE_INVENTORY_DURABILITY") + self:RegisterEvent("MERCHANT_SHOW") + self:SetScript("OnEvent", function(self, event) + if ( event == "MERCHANT_SHOW" and db.autorepair and CanMerchantRepair() ) then + local repCost, totCost = GetRepairAllCost(), 0 + if ( repCost > 0 ) then + if ( CanGuildBankRepair() and db.usegfunds ) then + RepairAllItems(1) + print(string.format("|cff6698FFSLDataText|r: %s %s.", L["GFAutoRepairLine"], convertMoney(repCost, true))) + else + RepairAllItems() + print(string.format("|cff6698FFSLDataText|r: %s %s.", L["AutoRepairLine"], convertMoney(repCost, true))) + end + end + else self:Refresh() end + end) + end + self:Refresh() +end + +function SLDT.Armor:Disable() + if ( not db.enabled ) then + self:UnregisterEvent("UPDATE_INVENTORY_DURABILITY") + self:UnregisterEvent("MERCHANT_SHOW") + end + self:Refresh() +end + +local tags = { + ["Dur"] = function() + durMin, durCol = 100, "ffffff" + for i = 1, 18 do + local durCur, durMax = GetInventoryItemDurability(i) + if ( durCur ~= durMax ) then durMin = min(durMin, durCur*(100/durMax)) end + end + if ( durMin < 60 ) then durCol = "ffff00" elseif ( durMin < 30 ) then durCol = "ff0000" end + return string.format("|cff%s%.0f|r|cff%s", durCol, durMin, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end, +} + +function SLDT.Armor:Refresh() + if ( db.enabled or SLDataText.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + local str = db.textDisplay + str = string.gsub(str, "%[(%w+)%]", function(w) return tags[w]() end) + text:SetFormattedText("|cff%s%s|r", SLDT.db.profile.cCol and SLDT.classColor or "ffffff", str) + + SLDT:UpdateBaseFrame(self, db) + else + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +SLDT.Armor.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "toggle", [2] = L["Auto Repair"], [3] = "autorepair" }, + [7] = { [1] = "toggle", [2] = L["Use Guild Bank"], [3] = "usegfunds" }, + [8] = { [1] = "text", [2] = L["Text Display"], [3] = "textDisplay" }, + [9] = { [1] = "desc", [2] = "ArmorTextDesc", [3] = L["ArmorTextDesc"] }, + [10] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [11] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [12] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [13] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [14] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [15] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [16] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [17] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + +local function OnInit() + SLDT.Armor.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.Armor.db:RegisterDefaults({ + profile = { + name = "Armor", + enabled = true, + autorepair = false, + usegfunds = false, + forceShow = false, + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOMLEFT", + xOff = 449, + yOff = 7, + strata = "LOW", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + tooltipOn = true, + textDisplay = "Armor [Dur]%", + }, + }) + db = SLDT.Armor.db.profile + + SLDT.Modules = SLDT.Modules or {} + if ( not SLDT.Modules[MODNAME] ) then table.insert(SLDT.Modules, { MODNAME, db }) end + frame, text, tool = SLDT:SetupBaseFrame(SLDT.Armor) + SetupToolTip() + + SLDT.Armor:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Armor:Enable() +end + +SLDT.Armor:RegisterEvent("PLAYER_ENTERING_WORLD") +SLDT.Armor:SetScript("OnEvent", OnInit) \ No newline at end of file diff --git a/Elements/bag.lua b/Elements/bag.lua new file mode 100644 index 0000000..374fe69 --- /dev/null +++ b/Elements/bag.lua @@ -0,0 +1,173 @@ +--[[ SLDataText Module: Bag ]] +--[[ Author: Taffu RevDate: 01/21/2018 Version: 7.3.1 ]] + +local SLDT, MODNAME = SLDataText, "Bag" +if ( SLDT ) then SLDT.Bag = CreateFrame("Frame") end +local L = SLDT.Locale +local db, frame, text, tool + +local function convertMoney(moolah, display) + local g, s, c = abs(moolah/10000), abs(mod(moolah/100, 100)), abs(mod(moolah, 100)) + local cash + if ( display ) then -- True = Long display + if ( g < 1 ) then g = "" else g = string.format("%d|cffffd700g|r ", g) end + if ( s < 1 ) then s = "" else s = string.format("%d|cffc7c7cfs|r ", s) end + c = string.format("%d|cffeda55fc|r", c) + cash = string.format("%s%s%s", g, s, c) + else + cash = string.format("%.1f|cffffd700g|r", g) + end + return cash +end + +local function SetupToolTip() + tool:SetScript("OnEnter", function(this) + GameTooltip:SetOwner(this, db.aF) + local bagRem, bagTtl = 0, 0 + for i = 0, NUM_BAG_SLOTS do + bagRem, bagTtl = bagRem + GetContainerNumFreeSlots(i), bagTtl + GetContainerNumSlots(i) + end + GameTooltip:AddLine("|cffffffff"..L["Bag Info"].."|r") + GameTooltip:AddDoubleLine(L["Space Used"], string.format("%d", bagTtl - bagRem), 1,1,0,1,1,1) + GameTooltip:AddDoubleLine(L["Space Avail"], string.format("%d", bagTtl), 1,1,0,1,1,1) + GameTooltip:AddDoubleLine(L["Space Left"], string.format("%d", bagRem), 1,1,0,1,1,1) + GameTooltip:AddLine(" ") + GameTooltip:AddDoubleLine(L["AutoSell Junk"], string.format("%s", db.selljunk and "On" or "Off"), 1,1,0,1,1,1) + GameTooltip:AddLine(" ") + GameTooltip:AddDoubleLine(L["Left-Click"], L["Toggle Bags"], 1,1,0,1,1,1) + GameTooltip:Show() + end) + tool:SetScript("OnLeave", function(this) if ( GameTooltip:IsShown() ) then GameTooltip:Hide() end end) + tool:SetScript("OnMouseDown", function(this, button) + if ( button == "LeftButton" ) then OpenAllBags() end + end) +end + +function SLDT.Bag:Enable() + if ( db.enabled ) then + SLDT:UpdateBaseText(self, db) + self:RegisterEvent("BAG_UPDATE") + self:RegisterEvent("MERCHANT_SHOW") + self:SetScript("OnEvent", function(self, event) + if ( event == "MERCHANT_SHOW" and db.selljunk ) then + local junkMon = 0 + for bag = 0, NUM_BAG_SLOTS do + for slot = 0, GetContainerNumSlots(bag) do + local link = GetContainerItemLink(bag, slot) + if ( link ) then + if ( select(3, GetItemInfo(link)) == 0 ) then + junkMon = junkMon + select(11, GetItemInfo(link)) * select(2, GetContainerItemInfo(bag, slot)) + UseContainerItem(bag, slot) + end + end + end + end + if ( junkMon > 0 ) then print(string.format("|cff6698FFSLDataText|r: %s %s", L["JunkSoldLine"], convertMoney(junkMon, true))) end + self:Refresh() + else self:Refresh() end + end) + end + self:Refresh() +end + +function SLDT.Bag:Disable() + if ( not db.enabled ) then + self:UnregisterEvent("BAG_UPDATE") + self:UnregisterEvent("MERCHANT_SHOW") + end + self:Refresh() +end + +local tags = { + ["T"] = function() + local total = 0 + for i = 0, NUM_BAG_SLOTS do + total = total + GetContainerNumSlots(i) + end + return string.format("|cffffffff%s|r|cff%s", total, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end, + ["U"] = function() + local rem, total = 0, 0 + for i = 0, NUM_BAG_SLOTS do + rem, total = rem + GetContainerNumFreeSlots(i), total + GetContainerNumSlots(i) + end + return string.format("|cffffffff%s|r|cff%s", total-rem, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end, + ["R"] = function() + local rem = 0 + for i = 0, NUM_BAG_SLOTS do + rem = rem + GetContainerNumFreeSlots(i) + end + return string.format("|cffffffff%s|r|cff%s", rem, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end, +} + +function SLDT.Bag:Refresh() + if ( db.enabled or SLDataText.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + local str = db.textDisplay + str = string.gsub(str, "%[(%w+)%]", function(w) return tags[w]() end) + text:SetFormattedText("|cff%s%s|r", SLDT.db.profile.cCol and SLDT.classColor or "ffffff", str) + + SLDT:UpdateBaseFrame(SLDT.Bag, db) + else + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +SLDT.Bag.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "toggle", [2] = L["AutoSell Junk"], [3] = "selljunk" }, + [7] = { [1] = "text", [2] = L["Text Display"], [3] = "textDisplay" }, + [8] = { [1] = "desc", [2] = "BagTextDesc", [3] = L["BagTextDesc"] }, + [9] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [10] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [11] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [12] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [13] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [14] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [15] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [16] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + + +local function OnInit() + SLDT.Bag.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.Bag.db:RegisterDefaults({ + profile = { + name = "Bag", + enabled = true, + selljunk = false, + forceShow = false, + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOMLEFT", + xOff = 364, + yOff = 7, + strata = "LOW", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + tooltipOn = true, + textDisplay = "Bag: [R]/[T]", + }, + }) + db = SLDT.Bag.db.profile + + SLDT.Modules = SLDT.Modules or {} + if ( not SLDT.Modules[MODNAME] ) then table.insert(SLDT.Modules, { MODNAME, db }) end + frame, text, tool = SLDT:SetupBaseFrame(SLDT.Bag) + SetupToolTip() + + SLDT.Bag:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Bag:Enable() +end + +SLDT.Bag:RegisterEvent("PLAYER_ENTERING_WORLD") +SLDT.Bag:SetScript("OnEvent", OnInit) \ No newline at end of file diff --git a/Elements/clock.lua b/Elements/clock.lua new file mode 100644 index 0000000..1b9cde0 --- /dev/null +++ b/Elements/clock.lua @@ -0,0 +1,329 @@ +--[[ SLDataText Module: Clock ]] +--[[ Author: Taffu RevDate: 01/21/2018 Version: 7.3.1 ]] + +-- Updated by Suicidal Katt +-- Added additional toggle for "Custom Time Format", previously the custom string was only used if realmTime was not used. +-- Added additional toggle for "Military Time" and added support for the db value 'format24'. +-- Fix: Custom Time formatting will use class colors if used and will lowercase the am/pm for any instance of %p throughout the string. +-- Fix: 'hourCorrect' will now work on any instance of %H or %I throughout the string. +-- Fix: Realm Time will now toggle between local and realm time for both custom strings and default formatting. +-- Added 'getLocalTime()' function to allow formatted text for local time. +-- Alteration: Options ordering has changed, see table below as well as the default value for the 'timeString'. +-- Note: A lot of my code could probably be shrunken down but I feel like this change is a pretty large one. Some additional localizations are needed. + + +local SLDT, MODNAME = SLDataText, "Clock" +if ( SLDT ) then SLDT.Clock = CreateFrame("Frame") end +local L = SLDT.Locale +local db, frame, text, tool + +local rCol, gCol = RED_FONT_COLOR_CODE, GREEN_FONT_COLOR_CODE +local locTime, rlmTime +local function getGameTime() + local serTime, serAMPM + local hour, minu = GetGameTime() + if ( minu < 10 ) then minu = string.format("0%i", minu) end + if ( db.format24 ) then + serAMPM = ""; serTime = string.format("%s:%s", hour, minu) + else + if ( hour > 11 ) then serAMPM = "pm" else serAMPM = "am" end + if ( hour == 0 ) then hour = hour + 12 elseif hour > 12 then hour = hour - 12 end + serTime = string.format("%s:%s", hour, minu) + end + return serTime, serAMPM +end + +local function getLocalTime() + local serTime, serAMPM + local hour, minu = tonumber(date("%H")),tonumber(date("%M")) + if ( minu < 10 ) then minu = string.format("0%i", minu) end + if ( db.format24 ) then + serAMPM = ""; serTime = string.format("%s:%s", hour, minu) + else + if ( hour > 11 ) then serAMPM = "pm" else serAMPM = "am" end + if ( hour == 0 ) then hour = hour + 12 elseif hour > 12 then hour = hour - 12 end + serTime = string.format("%s:%s", hour, minu) + end + return serTime, serAMPM +end + +local function formatTimer(wait, long) + local timestring + local h, m, s = 0, 0, 0 + if ( wait >= 3600 ) then + h = floor(wait / 3600); wait = wait - (h * 3600) + m = floor(wait / 60); wait = wait - (m * 60) + s = floor(wait) + + if ( m < 10 ) then m = string.format("%d%d", 0, m) end + if ( s < 10 ) then s = string.format("%d%d", 0, s) end + + if ( long ) then + timestring = string.format("%s hours", h) + else + timestring = string.format("%s:%s:%s", h, m, s) + end + elseif ( wait >= 60 and wait < 3600 ) then + m = floor(wait / 60); wait = wait - (m * 60) + s = floor(wait) + + if ( s < 10 ) then s = string.format("%d%d", 0, s) end + + if ( long ) then + timestring = string.format("%s min %s sec", m, s) + else + timestring = string.format("%s:%s", m, s) + end + elseif ( wait < 60 ) then + s = floor(wait) + + if ( long ) then + timestring = string.format("%s sec", s) + else + timestring = string.format("%s", s) + end + end + + return timestring +end + +local function SetupToolTip() + tool:SetScript("OnEnter", function(this) + GameTooltip:SetOwner(this, db.aF) + GameTooltip:AddLine(string.format("|cffffffff%s %i, %i|r", date("%B"), date("%d"), date("%Y"))) + GameTooltip:AddDoubleLine("Realm Time", string.format("%s%s", select(1, getGameTime()), select(2, getGameTime())), 1,1,0,1,1,1) + local hr, mi, mer = date("%I"), date("%M"), string.lower(date("%p")) + GameTooltip:AddDoubleLine("Local Time", string.format("%i:%s%s", hr, mi, mer), 1,1,0,1,1,1) + GameTooltip:AddLine(" ") + + if ( db.showPVP ) then + local inQueue = nil + for i = 1, 2 do + local id, name, active, canQ, wait, _ = GetWorldPVPAreaInfo(i) + if ( active ) then + name = string.format("%s%s (A)|r", rCol, name) + elseif ( canQ ) then + name = string.format("%s%s (Q)|r", gCol, name) + end + GameTooltip:AddDoubleLine(name, formatTimer(wait)) + end + + for j = 1, MAX_WORLD_PVP_QUEUES do + local status, map = GetWorldPVPQueueStatus(j) + if ( status == "queued" ) then inQueue = {}; table.insert(inQueue, map) end + end + + if ( inQueue ~= nil ) then + local maps = "" + for k, v in pairs(inQueue) do + maps = string.format("%s %s", maps, v) + end + GameTooltip:AddLine(string.format("%s %s", L["Queued for:"], maps)) + end + + GameTooltip:AddLine(" ") + end + + GameTooltip:AddDoubleLine(L["Left-Click"], L["Toggle Calendar"], 1,1,0,1,1,1) + GameTooltip:AddDoubleLine(L["Right-Click"], L["Toggle Time Manager"], 1,1,0,1,1,1) + GameTooltip:Show() + end) + tool:SetScript("OnLeave", function(this) + if ( GameTooltip:IsShown() ) then GameTooltip:Hide() end + end) + tool:SetScript("OnMouseDown", function(self, button) + if ( button == "LeftButton" ) then + ToggleCalendar() + elseif ( button == "RightButton" ) then + ToggleTimeManager() + end + end) +end + +function SLDT.Clock:Enable() + if ( db.enabled ) then + SLDT:UpdateBaseText(self, db) + frame:SetScript("OnUpdate", function(_, elapsed) + self:Refresh() + end) + end +end + +function SLDT.Clock:Disable() + if ( not db.enabled ) then + frame:SetScript("OnUpdate", nil) + end + self:Refresh() +end + +function SLDT.Clock:Refresh() + if ( db.enabled or SLDT.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + if ( TimeManagerClockButton:IsShown() ) then TimeManagerClockButton:Hide() end + + if db.customString then + local timeString = db.timeString + local hr12String,hr24String,amString + local hour,mns = GetGameTime() + -- Coding for this was found in the UIParent.lua beginning with the function on line 3854 'BetterDate'. + local function amFind() + if db.realmTime then + if ( hour > 11 ) then return "pm" else return "am" end + else + return strlower(tostring(date("%p"))) + end + end + amString = string.format("|cff%s%s|r", SLDT.db.profile.cCol and SLDT.classColor or "ffffff", amFind()) + timeString = gsub(timeString, "^%%p", amString) + timeString = gsub(timeString, "([^%%])%%p", "%1"..amString); -- Fix any other within the string. + + local hour12 + if ( hour == 0 ) then + hour12 = hour + 12 + elseif hour > 12 then + hour12 = hour - 12 + else + hour12 = hour + end + + if db.hourCorrect then + if db.realmTime then + if strfind(tostring(hour12),0) == 1 then -- If first character is a 0 then replace 0 with "" + hr12String = gsub(tostring(hour12), 0, "", 1) + else + hr12String = hour12 + end + if strfind(tostring(hour),0) == 1 then + hr24String = gsub(tostring(hour), 0, "", 1) + else + hr24String = hour + end + else + if strfind(tostring(date("%I")),0) == 1 then + hr12String = gsub(tostring(date("%I")), 0, "", 1) + else + hr12String = date("%I") + end + if strfind(tostring(date("%H")),0) == 1 then + hr24String = gsub(tostring(date("%H")), 0, "", 1) + else + hr24String = date("%H") + end + end + else + if db.realmTime then + hr12String = hour12 + hr24String = hour + else + hr12String = date("%I") + hr24String = date("%H") + end + end + timeString = gsub(timeString, "^%%I", hr12String) + timeString = gsub(timeString, "([^%%])%%I", "%1"..hr12String); + + timeString = gsub(timeString, "^%%H", hr24String) + timeString = gsub(timeString, "([^%%])%%H", "%1"..hr24String); + + text:SetText(date(timeString)) + else + rlmTime = string.format("%s|cff%s%s|r", select(1, getGameTime()), SLDT.db.profile.cCol and SLDT.classColor or "ffffff", select(2, getGameTime())) + locTime = string.format("%s|cff%s%s|r", select(1, getLocalTime()), SLDT.db.profile.cCol and SLDT.classColor or "ffffff", select(2, getLocalTime())) + if db.realmTime and rlmTime then + text:SetText(rlmTime) + elseif not db.realmTime and locTime then + text:SetText(locTime) + end + end + + if ( not self.Moving) then SLDT:UpdateBaseFrame(self, db) end + else + if ( not TimeManagerClockButton:IsShown() ) then TimeManagerClockButton:Show() end + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +SLDT.Clock.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "toggle", [2] = L["PvP Info"], [3] = "showPVP" }, + [7] = { [1] = "toggle", [2] = L["CorrHour"], [3] = "hourCorrect" }, + [8] = { [1] = "toggle", [2] = "Custom Time Format", [3] = "customString" }, -- Needs localization + [9] = { [1] = "desc", [2] = L["ClockDesc"], [3] = L["ClockDesc"] }, + [10] = { [1] = "text", [2] = L["Time String"], [3] = "timeString" }, + [11] = { [1] = "toggle", [2] = L["Realm Time"], [3] = "realmTime" }, + [12] = { [1] = "toggle", [2] = "Military Time", [3] = "format24" }, -- Needs localization + [13] = { [1] = "toggle", [2] = L["PvP Info"], [3] = "showPVP" }, + [14] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [15] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [16] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [17] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [18] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [19] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [20] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [21] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + +local function OnInit() + SLDT.Clock.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.Clock.db:RegisterDefaults({ + profile = { + name = "Clock", + enabled = true, + forceShow = false, + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOMLEFT", + xOff = 0, + yOff = 7, + strata = "MEDIUM", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + tooltipOn = true, + showPVP = true, + hourCorrect = true, + realmTime = false, + customString = false, + timeString = "%a, %b, %d %I:%M %p", + }, + }) + db = SLDT.Clock.db.profile + + SLDT.Modules = SLDT.Modules or {} + if ( not SLDT.Modules[MODNAME] ) then table.insert(SLDT.Modules, { MODNAME, db }) end + frame, text, tool = SLDT:SetupBaseFrame(SLDT.Clock) + SetupToolTip() + + SLDT.Clock:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Clock:Enable() +end + +SLDT.Clock:RegisterEvent("PLAYER_ENTERING_WORLD") +SLDT.Clock:SetScript("OnEvent", OnInit) + +--[[ WORKING TIME ESCAPES +%a abbreviated weekday name (e.g., Wed) +%A full weekday name (e.g., Wednesday) +%b abbreviated month name (e.g., Sep) +%B full month name (e.g., September) +%c date and time (e.g., 09/16/98 23:48:10) +%d day of the month (16) [01-31] +%H hour, using a 24-hour clock (23) [00-23] +%I hour, using a 12-hour clock (11) [01-12] +%M minute (48) [00-59] +%m month (09) [01-12] +%p either "am" or "pm" (pm) +%S second (10) [00-61] +%w weekday (3) [0-6 = Sunday-Saturday] +%x date (e.g., 09/16/98) +%X time (e.g., 23:48:10) +%Y full year (1998) +%y two-digit year (98) [00-99] +%% the character `% +]] \ No newline at end of file diff --git a/Elements/currency.lua b/Elements/currency.lua new file mode 100644 index 0000000..d6ff42c --- /dev/null +++ b/Elements/currency.lua @@ -0,0 +1,144 @@ +--[[ SLDataText Module: Currency ]] +--[[ Author: Taffu RevDate: 01/21/2018 Version: 7.3.1 ]] + +local SLDT, MODNAME, SLT = SLDataText, "Currency", LibStub("LibSLTip-1.0") +if ( SLDT ) then SLDT.Currency = CreateFrame("Frame") end +local L = SLDT.Locale +local db, frame, text, tool, tip + +local function SetupToolTip() + tool:SetScript("OnEnter", function(this) + tip = SLT:GetTooltip("SLDT_Currency", true) + SLT:AddHeader("SLDT_Currency", L["Currency"]) + + for k, v in pairs(SLDT.Currency.currTbl) do + local buttonFunc = function(self, button) + db["display"] = k + SLDT.Currency:Refresh() + end + + SLT:AddDoubleLine("SLDT_Currency", k, tostring(v), nil, nil, true, buttonFunc) + end + + SLT:AddFooter("SLDT_Currency", L["Click to set display currency."], nil) + if ( select(2, GetNumGuildMembers()) > 1 and not InCombatLockdown() ) then SLT:ShowTooltip("SLDT_Currency", frame) end + end) + tool:SetScript("OnLeave", function(this) SLT:ClearTooltip("SLDT_Currency") end) + tool:SetScript("OnMouseDown", function(this, button) + ToggleCharacter("TokenFrame") + end) +end + +local function TruncateName(name) + local first, second = string.split(" ", name) + return first +end + +function SLDT.Currency:Enable() + if ( db.enabled ) then + SLDT:UpdateBaseText(self, db) + self:RegisterEvent("CURRENCY_DISPLAY_UPDATE") + self:SetScript("OnEvent", function() self:Refresh() end) + end + self:Refresh() +end + +function SLDT.Currency:Disable() + if ( not db.enabled ) then + self:UnregisterEvent("CURRENCY_DISPLAY_UPDATE") + self:SetScript("OnEvent", nil) + end + self:Refresh() +end + +function SLDT.Currency:Refresh() + if ( db.enabled or SLDataText.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + SLDT.Currency.currTbl = {} + for i = 1, C_CurrencyInfo.GetCurrencyListSize() do + local currencyListInfo = C_CurrencyInfo.GetCurrencyListInfo(i) + -- local name, isHeader, isExpanded, isUnused, isWatched, count, extraCurrencyType, icon, itemID = GetCurrencyListInfo(i) + if ( not currencyListInfo.isHeader ) and ( not currencyListInfo.isTypeUnused ) then + SLDT.Currency.currTbl[currencyListInfo.name] = currencyListInfo.quantity + end + end + + if ( SLDT.Currency.currTbl[db.display] ) then + local line = TruncateName(db.display) + text:SetFormattedText("|cff%s%s:|r %i", SLDT.db.profile.cCol and SLDT.classColor or "ffffff", line, SLDT.Currency.currTbl[db.display]) + else + text:SetText(L["No Currency"]) + end + + SLDT:UpdateBaseFrame(SLDT.Currency, db) + else + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +local function GetCurrList() + local list = {} + table.insert(list, "None") + for i = 1, C_CurrencyInfo.GetCurrencyListSize() do + local currencyListInfo = C_CurrencyInfo.GetCurrencyListInfo(i) + + if ( not currencyListInfo.isHeader ) and ( not currencyListInfo.isTypeUnused ) then + table.insert(list, currencyListInfo.name) + end + end + return list +end + +SLDT.Currency.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [7] = { [1] = "select", [2] = L["Display Currency"], [3] = "display", [4] = GetCurrList() }, + [8] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [9] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [10] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [11] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [12] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [13] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [14] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + +local function OnInit() + SLDT.Currency.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.Currency.db:RegisterDefaults({ + profile = { + name = "Currency", + enabled = true, + display = "None", + forceShow = false, + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOM", + xOff = -84, + yOff = 7, + strata = "LOW", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + interval = 10, + tooltipOn = true, + }, + }) + db = SLDT.Currency.db.profile + + SLDT.Modules = SLDT.Modules or {} + if ( not SLDT.Modules[MODNAME] ) then table.insert(SLDT.Modules, { MODNAME, db }) end + frame, text, tool = SLDT:SetupBaseFrame(SLDT.Currency) + SetupToolTip() + + SLDT.Currency:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Currency:Enable() +end + +SLDT.Currency:RegisterEvent("PLAYER_ENTERING_WORLD") +SLDT.Currency:SetScript("OnEvent", OnInit) \ No newline at end of file diff --git a/Elements/exp.lua b/Elements/exp.lua new file mode 100644 index 0000000..8a5e20d --- /dev/null +++ b/Elements/exp.lua @@ -0,0 +1,175 @@ +--[[ SLDataText Module: Exp ]] +--[[ Author: Taffu RevDate: 01/21/2018 Version: 7.3.1 ]] + +-- Rev: Added tooltip + +local SLDT, MODNAME, SLT = SLDataText, "Exp", LibStub("LibSLTip-1.0") +if ( SLDT ) then SLDT.Exp = CreateFrame("Frame") end +local L = SLDT.Locale +local db, frame, text, tool + +local tags = { + ["Cur"] = function() + local curXP = UnitXP("player") + if ( curXP > 9999 ) then + return string.format("|cffffffff%.0fk|r|cff%s", curXP / 1000, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + else + return string.format("|cffffffff%.0f|r|cff%s", curXP, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end + end, + ["Max"] = function() + local maxXP = UnitXPMax("player") + if ( maxXP > 9999 ) then + return string.format("|cffffffff%.0fk|r|cff%s", maxXP / 1000, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + else + return string.format("|cffffffff%.0f|r|cff%s", maxXP, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end + end, + ["MaxRaw"] = function() + local maxXP = UnitXPMax("player") + return string.format("|cffffffff%.0f|r|cff%s", maxXP, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end, + ["Rem"] = function() + local remXP = UnitXPMax("player") - UnitXP("player") + if ( remXP > 9999 ) then + return string.format("|cffffffff%.0fk|r|cff%s", remXP / 1000, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + else + return string.format("|cffffffff%.0f|r|cff%s", remXP, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end + end, + ["Per"] = function() + local perXP = UnitXP("player") * (100 / UnitXPMax("player")) + return string.format("|cffffffff%.1f%%|r|cff%s", perXP, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end, + ["PerR"] = function() + local perRemXP = 100 - (UnitXP("player") * (100 / UnitXPMax("player"))) + return string.format("|cffffffff%.1f%%|r|cff%s", perRemXP, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end, + ["R"] = function() + local rest = GetXPExhaustion() or 0 + if ( rest > 9999 ) then + return string.format("|cffffffff%.0fk|r|cff%s", rest / 1000, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + else + return string.format("|cffffffff%.0f|r|cff%s", rest, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end + end, + ["RP"] = function() + local rem, rest = UnitXPMax("player") - UnitXP("player"), GetXPExhaustion() or 0 + local restPer = (100 / rem) * rest + return string.format("|cffffffff%.1f%%|r|cff%s", restPer, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end, +} + +local function SetupToolTip() + tool:SetScript("OnEnter", function(this) + if ( db.tooltipOn ) then + tip = SLT:GetTooltip("SLDT_Exp", false) + SLT:AddHeader("SLDT_Exp", UnitName("player"), "Level " .. UnitLevel("player"), {1, 1, 1}) + + SLT:AddDoubleLine("SLDT_Exp", "Current", tags["Cur"]() .. " (" .. tags["Per"]() .. ")") + SLT:AddDoubleLine("SLDT_Exp", "Needed", tags["MaxRaw"]()) + SLT:AddDoubleLine("SLDT_Exp", "Remaining", tags["Rem"]() .. " (" .. tags["PerR"]() .. ")") + + if ( GetXPExhaustion() ) then + SLT:AddDoubleLine("SLDT_Exp", "Rested", tags["R"]() .. " (" .. tags["RP"]() .. ")") + end + + if ( not InCombatLockdown() ) then SLT:ShowTooltip("SLDT_Exp", frame) end + end + end) + tool:SetScript("OnLeave", function(this) if ( db.tooltipOn ) then SLT:ClearTooltip("SLDT_Exp") end end) +end + +function SLDT.Exp:Enable() + if ( db.enabled ) then + SLDT:UpdateBaseText(self, db) + self:RegisterEvent("PLAYER_XP_UPDATE") + self:RegisterEvent("DISABLE_XP_GAIN") + self:RegisterEvent("ENABLE_XP_GAIN") + self:SetScript("OnEvent", function(self, event) self:Refresh() end) + end + self:Refresh() +end + +function SLDT.Exp:Disable() + if ( not db.enabled ) then + self:UnregisterEvent("PLAYER_XP_UPDATE") + self:UnregisterEvent("DISABLE_XP_GAIN") + self:UnregisterEvent("ENABLE_XP_GAIN") + self:SetScript("OnEvent", nil) + end + self:Refresh() +end + +function SLDT.Exp:Refresh() + if ( db.enabled or SLDataText.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + if ( db.hideMaxLvl and ( UnitLevel("player") == 110 ) ) then + text:SetText("") + else + local str = db.textDisplay + str = string.gsub(str, "%[(%w+)%]", function(w) return tags[w]() end) + text:SetFormattedText("|cff%s%s|r", SLDT.db.profile.cCol and SLDT.classColor or "ffffff", str) + end + + SLDT:UpdateBaseFrame(self, db) + else + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +SLDT.Exp.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "toggle", [2] = L["Max Level Hide"], [3] = "hideMaxLvl" }, + [7] = { [1] = "text", [2] = L["Text Display"], [3] = "textDisplay" }, + [8] = { [1] = "desc", [2] = "ExpTextDesc", [3] = L["ExpTextDesc"] }, + [9] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [10] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [11] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [12] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [13] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [14] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [15] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [16] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + +local function OnInit() + SLDT.Exp.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.Exp.db:RegisterDefaults({ + profile = { + name = "Exp", + enabled = true, + hideMaxLvl = false, + forceShow = false, + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOM", + xOff = 51, + yOff = 7, + strata = "LOW", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + tooltipOn = true, + textDisplay = "Exp [Cur]/[Max] ([Per])", + }, + }) + db = SLDT.Exp.db.profile + + SLDT.Modules = SLDT.Modules or {} + if ( not SLDT.Modules[MODNAME] ) then table.insert(SLDT.Modules, { MODNAME, db }) end + frame, text, tool = SLDT:SetupBaseFrame(SLDT.Exp) + SetupToolTip() + + SLDT.Exp:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Exp:Enable() +end + +SLDT.Exp:RegisterEvent("PLAYER_ENTERING_WORLD") +SLDT.Exp:SetScript("OnEvent", OnInit) \ No newline at end of file diff --git a/Elements/fps.lua b/Elements/fps.lua new file mode 100644 index 0000000..75efdfb --- /dev/null +++ b/Elements/fps.lua @@ -0,0 +1,100 @@ +--[[ SLDataText Module: FPS ]] +--[[ Author: Taffu RevDate: 01/21/2018 Version: 7.3.1 ]] + +local SLDT, MODNAME = SLDataText, "FPS" +if ( SLDT ) then SLDT.FPS = CreateFrame("Frame") end +local L = SLDT.Locale +local db, frame, text, tool + +function SLDT.FPS:Enable() + if ( db.enabled ) then + SLDT:UpdateBaseText(self, db) + local int = db.interval + frame:SetScript("OnUpdate", function(_, elapsed) + int = int - elapsed + if ( int <= 0 ) then self:Refresh(); int = db.interval end + end) + end + self:Refresh() +end + +function SLDT.FPS:Disable() + if ( not db.enabled ) then + frame:SetScript("OnUpdate", nil) + end + self:Refresh() +end + +local tags = { + ["F"] = function() + local fr = GetFramerate() + return string.format("|cffffffff%.0f|r|cff%s", fr, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end, +} + +function SLDT.FPS:Refresh() + if ( db.enabled or SLDataText.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + local str = db.textDisplay + str = string.gsub(str, "%[(%w+)%]", function(w) return tags[w]() end) + text:SetFormattedText("|cff%s%s|r", SLDT.db.profile.cCol and SLDT.classColor or "ffffff", str) + + SLDT:UpdateBaseFrame(self, db) + else + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +SLDT.FPS.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "text", [2] = L["Text Display"], [3] = "textDisplay" }, + [6] = { [1] = "desc", [2] = "FPSTextDesc", [3] = L["FPSTextDesc"] }, + [7] = { [1] = "range", [2] = L["Update Interval"], [3] = "interval", [4] = 10, [5] = 1000, [6] = 10 }, + [8] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [9] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [10] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [11] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [12] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [13] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [14] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [15] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + +local function OnInit() + SLDT.FPS.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.FPS.db:RegisterDefaults({ + profile = { + name = "FPS", + enabled = true, + forceShow = false, + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOMLEFT", + xOff = 517, + yOff = 7, + strata = "LOW", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + interval = 10, + tooltipOn = false, + textDisplay = "[F] fps", + }, + }) + db = SLDT.FPS.db.profile + + SLDT.Modules = SLDT.Modules or {} + if ( not SLDT.Modules[MODNAME] ) then table.insert(SLDT.Modules, { MODNAME, db }) end + frame, text, tool = SLDT:SetupBaseFrame(SLDT.FPS) + + SLDT.FPS:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.FPS:Enable() +end + +SLDT.FPS:RegisterEvent("PLAYER_ENTERING_WORLD") +SLDT.FPS:SetScript("OnEvent", OnInit) \ No newline at end of file diff --git a/Elements/friends.lua b/Elements/friends.lua new file mode 100644 index 0000000..73e41df --- /dev/null +++ b/Elements/friends.lua @@ -0,0 +1,193 @@ +--[[ SLDataText Module: Friends ]] +--[[ Author: Taffu RevDate: 08/02/2018 Version: 8.0.2 ]] + +-- Updated by Suicidal Katt +-- Fixed an issue with on click functions not closing the tooltip. +-- "InviteUnit" function calls need to be redone. + + +local addon, ns = ... +local SLDT, MODNAME, SLT, L = SLDataText, "Friends", LibStub("LibSLTip-1.0"), ns.L +if ( SLDT ) then SLDT.Friends = CreateFrame("Frame") end +local db, frame, text, tool, tip +local friendList, BNetList, friendsOn = {}, {}, 0 + +local function SetupToolTip() + tool:SetScript("OnEnter", function(this) + tip = SLT:GetTooltip("SLDT_Friends", true) + SLT:AddHeader("SLDT_Friends", L["Friend List"], string.format("%s: %i", L["Friends Online"], friendsOn)) + for k, v in pairs(friendList) do + local name, lvl, class, area, status, note = v[1], v[2], v[3], v[4], v[5], v[6] + --NOTE: Editing this out until Blizz lets classFileName become available @ Friend API level + --if ( class and class == "Death Knight" ) then class = "DEATHKNIGHT" else class = string.upper(class) end + --local cCol = string.format("%02X%02X%02X", RAID_CLASS_COLORS[class].r*255, RAID_CLASS_COLORS[class].g*255, RAID_CLASS_COLORS[class].b*255) + local lineL = string.format("%s %s %s", lvl, name, status or "") + local lineR = string.format("%s", area or "") + + local buttonFunc = function(self, button) + if ( IsAltKeyDown() ) then + InviteUnit(name) + else + SetItemRef("player:"..name, "|Hplayer:"..name.."|h["..name.."|h", "LeftButton") + end + SLT:ClearTooltip("SLDT_Friends") + end + + SLT:AddDoubleLine("SLDT_Friends", lineL, lineR, nil, nil, true, buttonFunc) + if ( note and db.showNote ) then + local noteLine = string.format(" - %s: %s", L["Note"], note) + SLT:AddLine("SLDT_Friends", noteLine, nil) + end + end + + if ( select("#", BNetList) >= 1 and select("#", friendList) >= 1 ) then + SLT:AddLine("SLDT_Friends", L["BNet Friends"]) + SLT:AddSpacer("SLDT_Friends") + end + + if ( BNetList and select("#", BNetList) >= 1 ) then + for k, v in pairs(BNetList) do + local BNid, BNname, battleTag, toonname, client, status, broadcast, note = v[1], v[2], v[3], v[4], v[5], v[6], v[7], v[8] + + local lineL = string.format("|cffecd672%s|r", BNname, battleTag, toonname) + local lineR = string.format("%s%s", status or "", client or "") + + local buttonFunc = function(self, button) + if ( IsAltKeyDown() ) then + if ( client == "WoW" ) then InviteUnit(toonname) end + else + local nameLine = string.format("%s : %s", BNname, BNid) + SetItemRef("BNplayer:"..nameLine, "|Hplayer:"..nameLine.."|h["..nameLine.."|h", "LeftButton") + end + SLT:ClearTooltip("SLDT_Friends") + end + + SLT:AddDoubleLine("SLDT_Friends", lineL, lineR, nil, nil, true, buttonFunc) + if ( note and db.showNote ) then + local noteLine = string.format(" - Note: %s", note) + SLT:AddLine("SLDT_Friends", noteLine, nil) + end + end + end + + SLT:AddFooter("SLDT_Friends", L["ClickDesc"], nil) + SLT:AddFooter("SLDT_Friends", L["AltClickDesc"], nil) + if ( friendsOn > 0 and not InCombatLockdown() ) then SLT:ShowTooltip("SLDT_Friends", frame) end + end) + tool:SetScript("OnLeave", function(this) SLT:ClearTooltip("SLDT_Friends") end) + tool:SetScript("OnMouseDown", function(this, button) + ToggleFriendsFrame(1) + end) +end + +function SLDT.Friends:Enable() + if ( db.enabled ) then + self:RegisterEvent("FRIENDLIST_UPDATE") + self:RegisterEvent("BN_FRIEND_ACCOUNT_ONLINE") + self:RegisterEvent("BN_FRIEND_ACCOUNT_OFFLINE") + self:SetScript("OnEvent", function() self:Refresh() end) + end + self:Refresh() +end + +function SLDT.Friends:Disable() + if ( not db.enabled ) then + self:UnregisterEvent("FRIENDLIST_UPDATE") + self:UnregisterEvent("BN_FRIEND_ACCOUNT_ONLINE") + self:UnregisterEvent("BN_FRIEND_ACCOUNT_OFFLINE") + end + self:Refresh() +end + +function SLDT.Friends:Refresh() + if ( db.enabled or SLDataText.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + friendList, BNetList, friendsOn = {}, {}, 0 + for i = 1, C_FriendList.GetNumFriends() do + local name, lvl, class, area, online, status, note = C_FriendList.GetFriendInfoByIndex(i) + if ( online ) then + friendsOn = friendsOn + 1 + friendList = friendList or {} + table.insert(friendList, { name, lvl, class, area, status, note }) + end + end + + for j = 1, BNGetNumFriends() do + local friendAccountInfo = C_BattleNet.GetFriendAccountInfo(j) + local battleTag = friendAccountInfo.battleTag + + if (friendAccountInfo.gameAccountInfo.isOnline) then + -- local _,name, _, realmName, _, faction, race, class, guild, area, lvl = BNGetToonInfo(toonid) + friendsOn = friendsOn + 1 + if (not battleTag) then battleTag = "[noTag]" end + friendList = friendList or {} + local status = "" + if (friendAccountInfo.isAFK) then status = L["(AFK)"] end; if ( friendAccountInfo.isDND ) then status = L["(DND)"] end + -- table.insert(BNetList, { BNid, BNname, battleTag, toonname, client, status, broadcast, note }) + table.insert(BNetList, { friendAccountInfo.bnetAccountID, friendAccountInfo.accountName, battleTag, friendAccountInfo.gameAccountInfo.characterName, friendAccountInfo.gameAccountInfo.clientProgram, status, friendAccountInfo.customMessage, friendAccountInfo.note }) + end + end + + local txstr = string.format("|T%s:0|t ", "Interface\\Icons\\Inv_cask_04") + text:SetFormattedText("%s|cff%s%s:|r %s", db.showIcon and txstr or "", SLDT.db.profile.cCol and SLDT.classColor or "ffffff", L["Friends"], friendsOn) + SLDT:UpdateBaseFrame(self, db) + else + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +SLDT.Friends.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "toggle", [2] = L["Show Icon"], [3] = "showIcon" }, + [7] = { [1] = "toggle", [2] = L["Show Note"], [3] = "showNote" }, + [8] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [9] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [10] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [11] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [12] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [13] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [14] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [15] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + +local function OnInit() + SLDT.Friends.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.Friends.db:RegisterDefaults({ + profile = { + name = "Friends", + enabled = true, + showNote = false, + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOMLEFT", + xOff = 189, + yOff = 7, + strata = "LOW", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + tooltipOn = true, + forceShow = false, + showIcon = true, + }, + }) + db = SLDT.Friends.db.profile + + SLDT:AddModule(MODNAME, db) + frame, text, tool = SLDT:SetupBaseFrame(SLDT.Friends) + SetupToolTip() + + SLDT.Friends:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Friends:Enable() +end + +if ( IsAddOnLoaded("SLDataText") ) then + SLDT.Friends:RegisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Friends:SetScript("OnEvent", OnInit) +end \ No newline at end of file diff --git a/Elements/gold.lua b/Elements/gold.lua new file mode 100644 index 0000000..91fffe1 --- /dev/null +++ b/Elements/gold.lua @@ -0,0 +1,220 @@ +--[[ SLDataText Module: Gold ]] +--[[ Author: Taffu RevDate: 01/21/2018 Version: 7.3.1 ]] + +local SLDT, MODNAME = SLDataText, "Gold" +if ( SLDT ) then SLDT.Gold = CreateFrame("Frame") end +local L = SLDT.Locale +local db, realmDB, frame, text, tool + +local goldStart, goldEarned, loggedOn, curGold = 0, 0, true, 0 +local function convertMoney(moolah, display) + local g, s, c = abs(moolah/10000), abs(mod(moolah/100, 100)), abs(mod(moolah, 100)) + local cash + if ( display ) then -- True = Long display + if ( g < 1 ) then g = "" else g = string.format("%d|cffffd700g|r ", g) end + if ( s < 1 ) then s = "" else s = string.format("%d|cffc7c7cfs|r ", s) end + c = string.format("%d|cffeda55fc|r", c) + cash = string.format("%s%s%s", g, s, c) + else + cash = string.format("%.1f|cffffd700g|r", g) + end + return cash +end + +local function otherFaction(f) + if ( f == "Horde" ) then return "Alliance" else return "Horde" end +end + +local function SetupToolTip() + tool:SetScript("OnEnter", function(this) + GameTooltip:SetOwner(this, db.aF) + local current, sessStart, sessEarn = convertMoney(curGold, true), convertMoney(goldStart, true), convertMoney(goldEarned, true) + GameTooltip:AddLine(string.format("|cffffffff%s's "..L["Wallet"].."|r", UnitName("player"))) + GameTooltip:AddDoubleLine(L["Current"], current, 1,1,0,1,1,1) + GameTooltip:AddDoubleLine(L["Session Start"], sessStart, 1,1,0,1,1,1) + if ( curGold < goldStart ) then sessEarn = string.format("|cffffff00-(|r%s|cffffff00)|r", sessEarn) end + GameTooltip:AddDoubleLine(L["Session Earned"], sessEarn, 1,1,0,1,1,1) + + if ( db.altMoney ) then + local lined = false + for key, val in pairs(realmDB["Horde"]) do + if ( key ~= UnitName("player") ) then + if ( not lined ) then + GameTooltip:AddLine(" ") + GameTooltip:AddLine("|cffffff00"..L["Server Gold"].."|r") + GameTooltip:AddLine("-------------------------", 1, 1, 1) + GameTooltip:AddLine("|cffff0000"..L["Horde"].."|r") + lined = true + end + + local name, gold = key, 0 + for k, v in pairs(val) do + gold = v + end + GameTooltip:AddDoubleLine(name, convertMoney(gold, true), 1, 1, 1, 1, 1, 1) + end + end + local lined = false + for key, val in pairs(realmDB["Alliance"]) do + if ( key ~= UnitName("player") ) then + if ( not lined ) then + GameTooltip:AddLine(" ") + GameTooltip:AddLine("|cff0000ff"..L["Alliance"].."|r") + lined = true + end + + local name, gold = key, 0 + for k, v in pairs(val) do + gold = v + end + GameTooltip:AddDoubleLine(name, convertMoney(gold, true), 1, 1, 1, 1, 1, 1) + end + end + + local totalGold = 0 + local totalGoldH = 0 + local totalGoldA = 0 + for key, val in pairs(realmDB["Horde"]) do + for k, v in pairs(val) do + totalGold = totalGold + v + totalGoldH =totalGoldH + v + end + end + for key, val in pairs(realmDB["Alliance"]) do + for k, v in pairs(val) do + totalGold = totalGold + v + totalGoldA = totalGoldA +v + end + end + if ( totalGold > 0 ) then + GameTooltip:AddLine(" ") + GameTooltip:AddLine("-------------------------", 1, 1, 1) + GameTooltip:AddDoubleLine(L["Total Gold"], convertMoney(totalGold, true), 1, 1, 1, 1, 1, 1) + if( totalGoldH > 0 and totalGoldA > 0) then + GameTooltip:AddDoubleLine(L["Total Gold"].." |cffff0000"..L["Horde"].."|r", convertMoney(totalGoldH, true), 1, 1, 1, 1, 1, 1) + GameTooltip:AddDoubleLine(L["Total Gold"].." |cff0000ff"..L["Alliance"].."|r", convertMoney(totalGoldA, true), 1, 1, 1, 1, 1, 1) + end + end + end + + GameTooltip:Show() + end) + tool:SetScript("OnLeave", function(this) if ( GameTooltip:IsShown() ) then GameTooltip:Hide() end end) +end + +function SLDT.Gold:Enable() + if ( db.enabled ) then + SLDT:UpdateBaseText(self, db) + self:RegisterEvent("PLAYER_MONEY") + self:RegisterEvent("SEND_MAIL_MONEY_CHANGED") + self:RegisterEvent("SEND_MAIL_COD_CHANGED") + self:RegisterEvent("PLAYER_TRADE_MONEY") + self:RegisterEvent("TRADE_MONEY_CHANGED") + self:SetScript("OnEvent", function(self, event) self:Refresh() end) + end + self:Refresh() +end + +function SLDT.Gold:Disable() + if ( not db.enabled ) then + self:UnregisterEvent("PLAYER_MONEY") + self:UnregisterEvent("SEND_MAIL_MONEY_CHANGED") + self:UnregisterEvent("SEND_MAIL_COD_CHANGED") + self:UnregisterEvent("PLAYER_TRADE_MONEY") + self:UnregisterEvent("TRADE_MONEY_CHANGED") + self:SetScript("OnEvent", nil) + end + self:Refresh() +end + +function SLDT.Gold:Refresh() + if ( db.enabled or SLDataText.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + curGold = GetMoney() + realmDB[UnitFactionGroup("player")][UnitName("player")].gold = curGold + + local moneyTxt = convertMoney(curGold, db.display) + if ( loggedOn ) then + goldStart = curGold; loggedOn = false + else + if ( curGold - goldStart ~= 0 ) then goldEarned = curGold - goldStart end + end + text:SetText(moneyTxt) + + SLDT:UpdateBaseFrame(SLDT.Gold, db) + else + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +local resetPlayerData = function() + for k, v in pairs(realmDB[UnitFactionGroup("player")]) do + realmDB[UnitFactionGroup("player")][k] = nil + end +end + +SLDT.Gold.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "toggle", [2] = L["Display Style"], [3] = "display" }, + [7] = { [1] = "toggle", [2] = L["Alt Money"], [3] = "altMoney" }, + [8] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [9] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [10] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [11] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [12] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [13] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [14] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [15] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, + [16] = { [1] = "button", [2] = L["ResetData"], [3] = resetPlayerData }, +} + +local function OnInit() + SLDT.Gold.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.Gold.db:RegisterDefaults({ + profile = { + name = "Gold", + enabled = true, + display = false, + forceShow = false, + altMoney = true, + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOMLEFT", + xOff = 282, + yOff = 7, + strata = "LOW", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + tooltipOn = true, + }, + realm = { + [UnitFactionGroup("player")] = { + [UnitName("player")] = { + gold = 0, + }, + }, + [otherFaction(UnitFactionGroup("player"))] = { + }, + }, + }) + db = SLDT.Gold.db.profile + realmDB = SLDT.Gold.db.realm + + SLDT.Modules = SLDT.Modules or {} + if ( not SLDT.Modules[MODNAME] ) then table.insert(SLDT.Modules, { MODNAME, db }) end + frame, text, tool = SLDT:SetupBaseFrame(SLDT.Gold) + SetupToolTip() + + SLDT.Gold:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Gold:Enable() +end + +SLDT.Gold:RegisterEvent("PLAYER_ENTERING_WORLD") +SLDT.Gold:SetScript("OnEvent", OnInit) \ No newline at end of file diff --git a/Elements/guild.lua b/Elements/guild.lua new file mode 100644 index 0000000..39e7a3c --- /dev/null +++ b/Elements/guild.lua @@ -0,0 +1,198 @@ + --[[ SLDataText Module: Guild ]] +--[[ Author: Taffu RevDate: 08/02/2018 Version: 8.0.2 ]] + +-- Updated by Suicidal Katt +-- Class coloring returns in this version. +-- Player names are now using the Ambiguate function to remove realm info. +-- Guild Level now replaced with Guild Achievement Points as level was removed in patch 6.0.2 +-- Guild Tab reference has been removed - 8.0.2 + +local addon, ns = ... +local SLDT, MODNAME, SLT, L = SLDataText, "Guild", LibStub("LibSLTip-1.0"), ns.L +if ( SLDT ) then SLDT.Guild = CreateFrame("Frame") end +local db, frame, text, tool, tip +local guildName, guildMotto, guildRank, guildPoints, guildList + +local function SetupToolTip() + if ( not IsInGuild() ) then return end + tool:SetScript("OnEnter", function(this) + C_GuildInfo.GuildRoster() + SLDT.Guild:Refresh() + tip = SLT:GetTooltip("SLDT_Guild", true) + SLT:AddHeader("SLDT_Guild", string.format("%s (%s)", guildName or L["No Guild"], guildPoints or ""), guildMotto) + if select(2, GetNumGuildMembers()) >= 2 then + for key, val in pairs(guildList) do + local name, rank, level, class, zone, status, isMobile, note, oNote = val[1], val[2], val[3], val[4], val[5], val[6], val[7], val[8], val[9] + + if ( name ~= UnitName("player") ) then + local cCol = string.format("%02X%02X%02X", RAID_CLASS_COLORS[class].r*255, RAID_CLASS_COLORS[class].g*255, RAID_CLASS_COLORS[class].b*255) + local lineL = string.format("%s |cff%s%s|r %s", level, cCol, name, status or "") + local lineR = string.format("%s%s", isMobile and "|cffffff00[M]|r " or "", zone or "") + + local buttonFunc = function(self, button) + if ( IsAltKeyDown() ) then + InviteUnit(name) + else + SetItemRef("player:"..name, "|Hplayer:"..name.."|h["..name.."|h", "LeftButton") + end + end + + SLT:AddDoubleLine("SLDT_Guild", lineL, lineR, nil, nil, true, buttonFunc) + if ( note and note ~= "" and db.showNote ) then + local noteLine = string.format(" - Note: %s", note) + SLT:AddLine("SLDT_Guild", noteLine, nil) + end + if ( oNote and oNote ~= "" and db.showONote ) then + local noteLine = string.format(" - Officer: %s", oNote) + SLT:AddLine("SLDT_Guild", noteLine, nil) + end + else + + end + end + end + + SLT:AddFooter("SLDT_Guild", L["ClickDesc"], nil) + SLT:AddFooter("SLDT_Guild", L["AltClickDesc"], nil) + + if ( not db.showTTCombat and select(2, GetNumGuildMembers()) > 1 ) then + if ( not InCombatLockdown() ) then SLT:ShowTooltip("SLDT_Guild", frame) end + else + SLT:ShowTooltip("SLDT_Guild", frame) + end + end) + tool:SetScript("OnLeave", function(this) SLT:ClearTooltip("SLDT_Guild") end) + tool:SetScript("OnMouseDown", function(this, button) + ToggleGuildFrame() + --[[if ( IsInGuild() ) then + GuildFrameTab2:Click() + end]]-- + end) +end + +local int = 10 +function SLDT.Guild:RefreshTimer() + self:SetScript("OnUpdate", function(self, elapsed) + int = int - elapsed + if ( int <= 0 ) then + int = 10; self:Refresh() + self:SetScript("OnUpdate", nil) + end + end) +end + +function SLDT.Guild:Enable() + if ( db.enabled ) then + self:RegisterEvent("GUILD_ROSTER_UPDATE") + self:RegisterEvent("GUILD_TRADESKILL_UPDATE") + self:RegisterEvent("GUILD_MOTD") + self:RegisterEvent("GUILD_NEWS_UPDATE") + self:RegisterEvent("PLAYER_GUILD_UPDATE") + end + self:Refresh() +end + +function SLDT.Guild:Disable() + if ( not db.enabled ) then + self:UnregisterEvent("GUILD_ROSTER_UPDATE") + self:UnregisterEvent("GUILD_TRADESKILL_UPDATE") + self:UnregisterEvent("GUILD_MOTD") + self:UnregisterEvent("GUILD_NEWS_UPDATE") + self:UnregisterEvent("PLAYER_GUILD_UPDATE") + end + self:Refresh() +end + +function SLDT.Guild:Refresh() + if ( db.enabled or SLDataText.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + if ( IsInGuild() ) then + guildList = {} + guildName, guildRank, _ = GetGuildInfo("player") + guildMotto, guildPoints = GetGuildRosterMOTD(), GetTotalAchievementPoints(true) + + for i = 0, select(1, GetNumGuildMembers()) do + local name, rank, rankIndex, level, class, zone, note, officernote, online, status, classFileName, achievementPoints, achievementRank, isMobile, canSoR = GetGuildRosterInfo(i) + if ( online ) then + if ( status ~= nil and status == 0 ) then status = nil else status = L["(AFK)"] end + table.insert(guildList, { Ambiguate(name, "guild"), rank, level, classFileName, zone, status, isMobile, note, officernote }) + end + end + + local txstr + if ( UnitFactionGroup("player") == "Alliance" ) then + txstr = string.format("|T%s:0|t ", "Interface\\Icons\\Inv_bannerpvp_02") + else + txstr = string.format("|T%s:0|t ", "Interface\\Icons\\Inv_bannerpvp_01") + end + text:SetFormattedText("%s|cff%s%s:|r %s", db.showIcon and txstr or "", SLDT.db.profile.cCol and SLDT.classColor or "ffffff", L["Guild"], select(2, GetNumGuildMembers())) + else + text:SetText(L["No Guild"]) + end + + SLDT:UpdateBaseFrame(SLDT.Guild, db) + else + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +SLDT.Guild.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "toggle", [2] = L["Show Tooltip (Combat)"], [3] = "showTTCombat" }, + [7] = { [1] = "toggle", [2] = L["Show Icon"], [3] = "showIcon" }, + [8] = { [1] = "toggle", [2] = L["Show Note"], [3] = "showNote" }, + [9] = { [1] = "toggle", [2] = L["Show Officer Note"], [3] = "showONote" }, + [10] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [11] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [12] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [13] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [14] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [15] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [16] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [17] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + +local function OnInit() + SLDT.Guild.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.Guild.db:RegisterDefaults({ + profile = { + name = "Guild", + enabled = true, + showNote = false, + showONote = false, + showTTCombat = false, + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOMLEFT", + xOff = 88, + yOff = 7, + strata = "LOW", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + tooltipOn = true, + forceShow = false, + showIcon = true, + }, + }) + db = SLDT.Guild.db.profile + + SLDT:AddModule(MODNAME, db) + frame, text, tool = SLDT:SetupBaseFrame(SLDT.Guild) + SetupToolTip() + + SLDT.Guild:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Guild:SetScript("OnEvent", function() SLDT.Guild:Refresh() end) + SLDT.Guild:Enable() +end + +if ( IsAddOnLoaded("SLDataText") ) then + SLDT.Guild:RegisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Guild:SetScript("OnEvent", OnInit) +end \ No newline at end of file diff --git a/Elements/latency.lua b/Elements/latency.lua new file mode 100644 index 0000000..fa1ca2d --- /dev/null +++ b/Elements/latency.lua @@ -0,0 +1,116 @@ +--[[ SLDataText Module: Latency ]] +--[[ Author: Taffu RevDate: 01/21/2018 Version: 7.3.1 ]] + +local SLDT, MODNAME = SLDataText, "Latency" +if ( SLDT ) then SLDT.Latency = CreateFrame("Frame") end +local L = SLDT.Locale +local db, frame, text, tool + +local bandIn, bandOut, lagHome, lagWorld +local function SetupToolTip() + tool:SetScript("OnEnter", function(this) + GameTooltip:SetOwner(this, db.aF) + GameTooltip:AddLine("|cffffffff"..L["Latency"].."|r") + GameTooltip:AddDoubleLine(L["Bandwidth In"], string.format("%.2fkb", bandIn), 1,1,0,1,1,1) + GameTooltip:AddDoubleLine(L["Bandwidth Out"], string.format("%.2fkb", bandOut), 1,1,0,1,1,1) + GameTooltip:AddDoubleLine(L["Latency (Home)"], string.format("%ims", lagHome), 1,1,0,1,1,1) + GameTooltip:AddDoubleLine(L["Latency (World)"], string.format("%ims", lagWorld), 1,1,0,1,1,1) + GameTooltip:Show() + end) + tool:SetScript("OnLeave", function(this) if ( GameTooltip:IsShown() ) then GameTooltip:Hide() end end) +end + +function SLDT.Latency:Enable() + if ( db.enabled ) then + SLDT:UpdateBaseText(self, db) + local int = db.interval + frame:SetScript("OnUpdate", function(_, elapsed) + int = int - elapsed + if ( int <= 0 ) then self:Refresh(); int = db.interval end + end) + end + self:Refresh() +end + +function SLDT.Latency:Disable() + if ( not db.enabled ) then + frame:SetScript("OnUpdate", nil) + end + self:Refresh() +end + +local tags = { + ["L"] = function() + bandIn, bandOut, lagHome, lagWorld = GetNetStats() + return string.format("|cffffffff%i|r|cff%s", lagHome, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end, +} + +function SLDT.Latency:Refresh() + if ( db.enabled or SLDataText.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + local str = db.textDisplay + str = string.gsub(str, "%[(%w+)%]", function(w) return tags[w]() end) + text:SetFormattedText("|cff%s%s|r", SLDT.db.profile.cCol and SLDT.classColor or "ffffff", str) + + SLDT:UpdateBaseFrame(self, db) + else + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +SLDT.Latency.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "text", [2] = L["Text Display"], [3] = "textDisplay" }, + [7] = { [1] = "desc", [2] = "LagTextDesc", [3] = L["LagTextDesc"] }, + [8] = { [1] = "range", [2] = L["Update Interval"], [3] = "interval", [4] = 10, [5] = 1000, [6] = 10 }, + [9] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [10] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [11] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [12] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [13] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [14] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [15] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [16] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + +local function OnInit() + SLDT.Latency.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.Latency.db:RegisterDefaults({ + profile = { + name = "Latency", + enabled = true, + forceShow = false, + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOM", + xOff = -498, + yOff = 7, + strata = "LOW", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + interval = 10, + tooltipOn = true, + textDisplay = "[L]ms", + }, + }) + db = SLDT.Latency.db.profile + + SLDT.Modules = SLDT.Modules or {} + if ( not SLDT.Modules[MODNAME] ) then table.insert(SLDT.Modules, { MODNAME, db }) end + frame, text, tool = SLDT:SetupBaseFrame(SLDT.Latency) + SetupToolTip() + + SLDT.Latency:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Latency:Enable() +end + +SLDT.Latency:RegisterEvent("PLAYER_ENTERING_WORLD") +SLDT.Latency:SetScript("OnEvent", OnInit) \ No newline at end of file diff --git a/Elements/mail.lua b/Elements/mail.lua new file mode 100644 index 0000000..2603d41 --- /dev/null +++ b/Elements/mail.lua @@ -0,0 +1,231 @@ +--[[ SLDataText Module: Mail ]] +--[[ Author: Taffu RevDate: 08/02/2018 Version: 8.0.2 ]] + +-- Updated by Suicidal Katt +-- Fixed an issue with PlaySound call incorrectly argumented +-- Removed the "count" value if no mail has been counted. + +local SLDT, MODNAME = SLDataText, "Mail" +if ( SLDT ) then SLDT.Mail = CreateFrame("Frame") end +local L = SLDT.Locale +local db, frame, text, tool + +local handler = { + NOMAILICON = "Interface\\CURSOR\\UnableMail", + NEWMAILICON = "Interface\\Icons\\INV_Letter_09", + AHICON = "Interface\\Icons\\Ability_Paladin_JudgementofthePure", + MAILSOUND = "Interface\\AddOns\\SLDataText\\Media\\mail.mp3", + AHSOUND = 5274, + new = 0, + total = 0, + lastClose = 0, + ignoreNext = false, + mailChecked = false, + iconString = "|TInterface\\CURSOR\\UnableMail:0|t", + textString = L["No Mail"], +} + +local function SetupToolTip() + tool:SetScript("OnEnter", function(this) + if ( not HasNewMail() ) then return end + GameTooltip:SetOwner(this, db.aF) + MinimapMailFrameUpdate() + GameTooltip:Show() + end) + tool:SetScript("OnLeave", function(this) if ( GameTooltip:IsVisible() ) then GameTooltip:Hide() end end) +end + +local function UpdateDisplay() + if ( MiniMapMailFrame:IsVisible() ) then MiniMapMailFrame:Hide() end + + if ( db["ahAlert"] ) then + -- Change icon to AHAlert icon + handler.iconString = string.format("|T%s:0|t", handler.AHICON) + handler.textString = L["AH Alert!"] + elseif ( db["total"] and db["total"] > 0 ) or ( HasNewMail() and not handler.mailChecked ) then + -- Change icon to Mail icon + handler.iconString = string.format("|T%s:0|t", handler.NEWMAILICON) + handler.textString = L["Mail!"] + else + -- Change icon to No Mail icon + handler.iconString = string.format("|T%s:0|t", handler.NOMAILICON) + handler.textString = L["No Mail"] + end +end + +local function IncomingMail() + if ( handler.ignoreNext ) then + handler.ignoreNext = false + else + handler.new = 0 + if ( db["new"] ~= nil ) then + handler.new = db["new"] + (1 * .5) + end + + handler.total = 0 + if ( db["total"] ~= nil ) then + handler.total = db["total"] + .5 + end + + if ( handler.mailChecked ) then + handler.total = GetInboxNumItems() + handler.new + end + + db["new"] = handler.new + db["total"] = handler.total + + if ( db.playSounds ) then PlaySoundFile(handler.MAILSOUND) end + end +end + +local function ReadMsg(msg) + local ahEvents = { + [ERR_AUCTION_WON_S] = false, + [ERR_AUCTION_SOLD_S] = false, + [ERR_AUCTION_OUTBID_S] = true, + [ERR_AUCTION_EXPIRED_S] = false, + [ERR_AUCTION_REMOVED_S] = false, + } + + for k, _ in pairs(ahEvents) do + local search = string.gsub(k, "%%[^%s]+", "(.+)") + local _, _, item = string.find(msg, search) + + if ( item ) then + db["ahAlert"] = true + + if ( ahEvents[k[1]] ) then + IncomingMail() + end + + PlaySound(handler.AHSOUND) + end + end +end + +function SLDT.Mail:Enable() + if ( db.enabled ) then + SLDT:UpdateBaseText(self, db) + self:RegisterEvent("PLAYER_ENTERING_WORLD") + self:RegisterEvent("UPDATE_PENDING_MAIL") + self:RegisterEvent("MAIL_INBOX_UPDATE") + self:RegisterEvent("CHAT_MSG_SYSTEM") + self:RegisterEvent("MAIL_SHOW") + self:RegisterEvent("MAIL_CLOSED") + self:SetScript("OnEvent", function(self, event, ...) + if ( event == "PLAYER_ENTERING_WORLD" ) then + handler.ignoreNext = true + elseif ( event == "CHAT_MSG_SYSTEM" ) then + local arg = ... + ReadMsg(arg) + elseif ( event == "UPDATE_PENDING_MAIL" ) then + if ( (handler.lastClose + 5) > time() ) then + handler.ignoreNext = true + end + IncomingMail() + UpdateDisplay() + elseif ( event == "MAIL_INBOX_UPDATE" ) then + db["new"], db["total"] = 0, GetInboxNumItems() + UpdateDisplay() + elseif ( event == "MAIL_SHOW" ) then + handler.mailChecked = true + db["ahAlert"] = false + UpdateDisplay() + elseif ( event == "MAIL_CLOSED" ) then + handler.lastClose = time() + end + self:Refresh() + end) + end + handler.ignoreNext = true + self:Refresh() +end + +function SLDT.Mail:Disable() + if ( not db.enabled ) then + self:UnregisterEvent("UPDATE_PENDING_MAIL") + self:UnregisterEvent("MAIL_INBOX_UPDATE") + self:UnregisterEvent("CHAT_MSG_SYSTEM") + self:UnregisterEvent("MAIL_SHOW") + self:UnregisterEvent("MAIL_CLOSED") + self:SetScript("OnEvent", nil) + end + self:Refresh() +end + +function SLDT.Mail:Refresh() + if ( db.enabled or SLDataText.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + local count = "" + if ( db["total"] and db["total"] > 0 ) then + count = string.format("%u/%u", db["new"], db["total"]) + elseif ( HasNewMail() and not handler.mailChecked ) then + count = "" --L["Mail!"] + end + + text:SetFormattedText("%s%s%s", db.showIcon and handler.iconString.." " or "", db.showText and handler.textString.." " or "", count) + SLDT:UpdateBaseFrame(self, db) + else + if ( frame:IsVisible() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +SLDT.Mail.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "toggle", [2] = L["Show Icon"], [3] = "showIcon" }, + [7] = { [1] = "toggle", [2] = L["Show Text"], [3] = "showText" }, + [8] = { [1] = "toggle", [2] = L["Play Sounds"], [3] = "playSounds" }, + [9] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [10] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [11] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [12] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [13] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [14] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [15] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [16] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + +local function OnInit() + SLDT.Mail.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.Mail.db:RegisterDefaults({ + profile = { + name = "Mail", + enabled = true, + gfont = false, + outline = false, + forceShow = false, + tooltipOn = true, + showIcon = true, + showText = true, + playSounds = true, + fontSize = 14, + font = "Arial Narrow", + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOM", + xOff = -375, + yOff = 7, + strata = "LOW", + new = 0, + total = 0, + ahAlert = false, + }, + }) + db = SLDT.Mail.db.profile + + SLDT.Modules = SLDT.Modules or {} + if ( not SLDT.Modules[MODNAME] ) then table.insert(SLDT.Modules, { MODNAME, db }) end + frame, text, tool = SLDT:SetupBaseFrame(SLDT.Mail) + SetupToolTip() + + SLDT.Mail:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Mail:Enable() +end + +SLDT.Mail:RegisterEvent("PLAYER_ENTERING_WORLD") +SLDT.Mail:SetScript("OnEvent", OnInit) \ No newline at end of file diff --git a/Elements/memory.lua b/Elements/memory.lua new file mode 100644 index 0000000..e04a404 --- /dev/null +++ b/Elements/memory.lua @@ -0,0 +1,158 @@ +--[[ SLDataText Module: Memory ]] +--[[ Author: Taffu RevDate: 01/21/2018 Version: 7.3.1 ]] + +local SLDT, MODNAME = SLDataText, "Memory" +if ( SLDT ) then SLDT.Memory = CreateFrame("Frame") end +local L = SLDT.Locale +local db, frame, text, tool + +local function SetupToolTip() + tool:SetScript("OnEnter", function(this) + local function sortdesc(a, b) return a[2] > b[2] end + GameTooltip:SetOwner(this, db.aF) + UpdateAddOnMemoryUsage() + local addons, total = {}, 0 + for i = 1, GetNumAddOns() do + if ( IsAddOnLoaded(i) ) then + local memUse = GetAddOnMemoryUsage(i) + table.insert(addons, { GetAddOnInfo(i), memUse }) + total = total + memUse + end + end + table.sort(addons, sortdesc) + GameTooltip:AddLine(string.format("|cffffffff"..L["AddOn Memory"]..":|r %.1fmb", total/1024)) + if ( not IsAltKeyDown() ) then GameTooltip:AddLine(L["Showing Top 15 AddOns"]) end + GameTooltip:AddLine(" ") + for i = 1, #addons do + if ( i <= 15 and not IsAltKeyDown() ) then + local v = addons[i] + local tag, memAmt + if ( v[2]/1024 < 1 ) then tag = "kb"; memAmt = v[2] else tag = "mb"; memAmt = v[2]/1024 end + GameTooltip:AddDoubleLine(v[1], string.format("%.1f%s", memAmt, tag), 1,1,0,1,1,1) + elseif ( IsAltKeyDown() ) then + local v = addons[i] + local tag, memAmt + if ( v[2]/1024 < 1 ) then tag = "kb"; memAmt = v[2] else tag = "mb"; memAmt = v[2]/1024 end + GameTooltip:AddDoubleLine(v[1], string.format("%.1f%s", memAmt, tag), 1,1,0,1,1,1) + end + end + GameTooltip:AddDoubleLine("", "----------", 1,1,1,1,1,1) + GameTooltip:AddDoubleLine(L["Total AddOn Memory"], string.format("%.1fmb", total/1024), 1,1,0,1,1,1) + GameTooltip:AddDoubleLine(L["Total UI Memory Usage"], string.format("%.1fmb", gcinfo()/1024), 1,1,0,1,1,1) + GameTooltip:AddLine(" ") + GameTooltip:AddDoubleLine(L["Hover"], L["Show only top AddOns"], 1,1,0,1,1,1) + GameTooltip:AddDoubleLine(L["Alt+Hover"], L["Show all AddOns"], 1,1,0,1,1,1) + GameTooltip:AddDoubleLine(L["Right-Click"], L["Collect Garbage"], 1,1,0,1,1,1) + GameTooltip:Show() + end) + tool:SetScript("OnLeave", function(this) + if ( GameTooltip:IsShown() ) then GameTooltip:Hide() end + end) + tool:SetScript("OnMouseDown", function(self, button) + if ( button == "RightButton" ) then + collectgarbage() + end + end) +end + +function SLDT.Memory:Enable() + if ( db.enabled ) then + SLDT:UpdateBaseText(self, db) + local int = db.interval + frame:SetScript("OnUpdate", function(_, elapsed) + int = int - elapsed + if ( int <= 0 ) then SLDT.Memory:Refresh(); int = db.interval end + end) + end + self:Refresh() +end + +function SLDT.Memory:Disable() + if ( not db.enabled ) then + frame:SetScript("OnUpdate", nil) + end + self:Refresh() +end + +local tags = { + ["MA"] = function() + local total = 0 + for i = 1, GetNumAddOns() do + if ( IsAddOnLoaded(i) ) then total = total + GetAddOnMemoryUsage(i) end + end + return string.format("|cffffffff%.1f|r|cff%s", total/1024, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end, + ["MT"] = function() + return string.format("|cffffffff%.1f|r|cff%s", gcinfo()/1024, SLDT.db.profile.cCol and SLDT.classColor or "ffffff") + end, +} + +function SLDT.Memory:Refresh() + if ( db.enabled or SLDT.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + UpdateAddOnMemoryUsage() + local str = db.textDisplay + str = string.gsub(str, "%[(%w+)%]", function(w) return tags[w]() end) + text:SetFormattedText("|cff%s%s|r", SLDT.db.profile.cCol and SLDT.classColor or "ffffff", str) + + SLDT:UpdateBaseFrame(self, db) + else + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +SLDT.Memory.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "text", [2] = L["Text Display"], [3] = "textDisplay" }, + [7] = { [1] = "desc", [2] = "MemTextDesc", [3] = L["MemTextDesc"] }, + [8] = { [1] = "range", [2] = L["Update Interval"], [3] = "interval", [4] = 10, [5] = 1000, [6] = 10 }, + [9] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [10] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [11] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [12] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [13] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [14] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [15] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [16] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + +local function OnInit() + SLDT.Memory.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.Memory.db:RegisterDefaults({ + profile = { + name = "Memory", + enabled = true, + forceShow = false, + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOM", + xOff = -443, + yOff = 7, + strata = "MEDIUM", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + interval = 10, + tooltipOn = true, + textDisplay = "[MA]mb", + }, + }) + db = SLDT.Memory.db.profile + + SLDT.Modules = SLDT.Modules or {} + if ( not SLDT.Modules[MODNAME] ) then table.insert(SLDT.Modules, { MODNAME, db }) end + frame, text, tool = SLDT:SetupBaseFrame(SLDT.Memory) + SetupToolTip() + + SLDT.Memory:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Memory:Enable() +end + +SLDT.Memory:RegisterEvent("PLAYER_ENTERING_WORLD") +SLDT.Memory:SetScript("OnEvent", OnInit) \ No newline at end of file diff --git a/Elements/reputation.lua b/Elements/reputation.lua new file mode 100644 index 0000000..5318991 --- /dev/null +++ b/Elements/reputation.lua @@ -0,0 +1,169 @@ +--[[ SLDataText Module: Reputation ]] +--[[ Author: Taffu RevDate: 01/21/2018 Version: 7.3.1 ]] + +-- Rev: Added proper "Tooltip On" check + +local SLDT, MODNAME, SLT = SLDataText, "Reputation", LibStub("LibSLTip-1.0") +if ( SLDT ) then SLDT.Reputation = CreateFrame("Frame") end +local L = SLDT.Locale +local db, frame, text, tool, tip, noWatch + +local standingTbl = { + [1] = L["Hated"], + [2] = L["Hostile"], + [3] = L["Unfriendly"], + [4] = L["Neutral"], + [5] = L["Friendly"], + [6] = L["Honored"], + [7] = L["Revered"], + [8] = L["Exalted"], + [9] = L["Paragon"], +} + +local stdCol = { + [1] = { r = 0.8, g = 0.3, b = 0.22 }, + [2] = { r = 0.8, g = 0.3, b = 0.22 }, + [3] = { r = 0.75, g = 0.27, b = 0 }, + [4] = { r = 0.9, g = 0.7, b = 0 }, + [5] = { r = 0, g = 0.6, b = 0.1 }, + [6] = { r = 0, g = 0.6, b = 0.1 }, + [7] = { r = 0, g = 0.6, b = 0.1 }, + [8] = { r = 0, g = 0, b = 1 }, +} + +local function SetupToolTip() + tool:SetScript("OnEnter", function(this) + if ( SLDT.Reputation.repTbl and noWatch ~= true and db.tooltipOn ) then + local repTbl = SLDT.Reputation.repTbl + + tip = SLT:GetTooltip("SLDT_Reputation", false) + SLT:AddHeader("SLDT_Reputation", repTbl[1], repTbl[2], { 1, 1, 1 }) + SLT:AddDoubleLine("SLDT_Reputation", standingTbl[repTbl[3]], string.format("%i/%i", repTbl[6]-repTbl[4], repTbl[5]-repTbl[4]), { stdCol[repTbl[3]].r, stdCol[repTbl[3]].g, stdCol[repTbl[3]].b }, nil) + + if ( not InCombatLockdown() ) then SLT:ShowTooltip("SLDT_Reputation", frame) end + end + end) + tool:SetScript("OnLeave", function(this) if ( SLDT.Reputation.repTbl and db.tooltipOn ) then SLT:ClearTooltip("SLDT_Reputation") end end) + tool:SetScript("OnMouseDown", function(this, button) + ToggleCharacter("ReputationFrame") + end) +end + +local function TruncateName(name) + local first, second = string.split(" ", name) + return first +end + +function SLDT.Reputation:Enable() + if ( db.enabled ) then + SLDT:UpdateBaseText(self, db) + self:RegisterEvent("CHAT_MSG_COMBAT_FACTION_CHANGE") + self:RegisterEvent("UPDATE_FACTION") + self:SetScript("OnEvent", function() self:Refresh() end) + end + self:Refresh() +end + +function SLDT.Reputation:Disable() + if ( not db.enabled ) then + self:UnregisterEvent("CHAT_MSG_COMBAT_FACTION_CHANGE") + self:UnregisterEvent("UPDATE_FACTION") + self:SetScript("OnEvent", nil) + end + self:Refresh() +end + +local repCheckTimer = function() + SLDT.Reputation:SetScript("OnUpdate", function(self, elapsed) + if ( GetNumFactions() > 0 ) then + self:SetScript("OnUpdate", nil) + self:Refresh() + end + end) +end + +function SLDT.Reputation:Refresh() + if ( db.enabled or SLDataText.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + if ( GetNumFactions() == 0 ) then repCheckTimer(); return end + + noWatch = true + SLDT.Reputation.repTbl = {} + for i = 1, GetNumFactions() do + local name, desc, sID, barMin, barMax, barVal, _, _, isHeader, _, hasRep, isWatched, _ = GetFactionInfo(i) + if ( not isHeader ) then + if ( isWatched ) then + -- Store for tooltip use + SLDT.Reputation.repTbl = { name, desc, sID, barMin, barMax, barVal } + + local repPer = (100/(barMax-barMin))*(barVal-barMin) + text:SetFormattedText("|cff%s%s:|r %.0f%%", SLDT.db.profile.cCol and SLDT.classColor or "ffffff", name, repPer) + text:SetTextColor(stdCol[sID].r, stdCol[sID].g, stdCol[sID].b) + noWatch = false + end + end + end + + if ( noWatch ) then + SLDT.Reputation.repTbl = nil + text:SetText(L["No Reputation"]) + text:SetTextColor(1, 1, 1) + end + + SLDT:UpdateBaseFrame(SLDT.Reputation, db) + else + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + end +end + +SLDT.Reputation.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [7] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [8] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [9] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [10] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [11] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [12] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [13] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + +local function OnInit() + SLDT.Reputation.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.Reputation.db:RegisterDefaults({ + profile = { + name = "Reputation", + enabled = true, + display = "None", + forceShow = false, + aP = "CENTER", + anch = "UIParent", + aF = "BOTTOM", + xOff = -247, + yOff = 7, + strata = "LOW", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + interval = 10, + tooltipOn = true, + }, + }) + db = SLDT.Reputation.db.profile + + SLDT.Modules = SLDT.Modules or {} + if ( not SLDT.Modules[MODNAME] ) then table.insert(SLDT.Modules, { MODNAME, db }) end + frame, text, tool = SLDT:SetupBaseFrame(SLDT.Reputation) + SetupToolTip() + + SLDT.Reputation:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.Reputation:Enable() +end + +SLDT.Reputation:RegisterEvent("PLAYER_ENTERING_WORLD") +SLDT.Reputation:SetScript("OnEvent", OnInit) \ No newline at end of file diff --git a/Elements/zonetext.lua b/Elements/zonetext.lua new file mode 100644 index 0000000..379ed38 --- /dev/null +++ b/Elements/zonetext.lua @@ -0,0 +1,164 @@ +--[[ SLDataText Module: Zone Text ]] +--[[ Author: Taffu RevDate: 01/21/2018 Version: 7.3.1 ]] + +local SLDT, MODNAME = SLDataText, "ZoneText" +if ( SLDT ) then SLDT.ZoneText = CreateFrame("Frame") end +local L = SLDT.Locale +local db, frame, text, tool + +local zoneName, subZoneName, pvpType, factionName +local zCol = { + ["sanctuary"] = { r = 0.41, b = 0.8, g = 0.94 }, + ["arena"] = { r = 1.0, b = 0.1, g = 0.1 }, + ["friendly"] = { r = 0.1, b = 1.0, g = 0.1 }, + ["hostile"] = { r = 1.0, b = 0.1, g = 0.1 }, + ["contested"] = { r = 1.0, b = 0.7, g = 0 }, + +} + +local function SetupToolTip() + tool:SetScript("OnEnter", function(this) + GameTooltip:SetOwner(this, db.aF) + GameTooltip:AddLine(zoneName, zCol[pvpType] and { zCol[pvpType].r, zCol[pvpType].b, zCol[pvpType].g } or { 1, 1, 1 }) + if ( subZoneName and subZoneName ~= "" ) then + GameTooltip:AddLine(subZoneName, 1, 1, 1) + end + if ( zCol[pvpType] ) then + if ( pvpType == "sanctuary" ) then + GameTooltip:AddLine(SANCTUARY_TERRITORY, zCol[pvpType].r, zCol[pvpType].b, zCol[pvpType].g) + elseif ( pvpType == "arena" ) then + GameTooltip:AddLine(FREE_FOR_ALL_TERRITORY, zCol[pvpType].r, zCol[pvpType].b, zCol[pvpType].g) + elseif ( pvpType == "friendly" ) then + GameTooltip:AddLine(format(FACTION_CONTROLLED_TERRITORY, factionName), zCol[pvpType].r, zCol[pvpType].b, zCol[pvpType].g) + elseif ( pvpType == "hostile" ) then + GameTooltip:AddLine(format(FACTION_CONTROLLED_TERRITORY, factionName), zCol[pvpType].r, zCol[pvpType].b, zCol[pvpType].g) + elseif ( pvpType == "contested" ) then + GameTooltip:AddLine(CONTESTED_TERRITORY, zCol[pvpType].r, zCol[pvpType].b, zCol[pvpType].g) + end + end + GameTooltip:Show() + end) + tool:SetScript("OnLeave", function(this) if ( GameTooltip:IsShown() ) then GameTooltip:Hide() end end) + tool:SetScript("OnMouseDown", function() + ToggleFrame(WorldMapFrame) + end) +end + +local function FixFrames(t) + if ( t ) then + -- MinimapZoneTextButton.Show = MiniMapWorldMapButton.Hide + -- MinimapBorderTop.Show = MiniMapWorldMapButton.Hide + -- MiniMapWorldMapButton.Show = MiniMapWorldMapButton.Hide + + if ( IsAddOnLoaded("Chinchilla") ) then + if ( Chinchilla_Location_Frame and Chinchilla_Location_Frame:IsShown() ) then + Chinchilla_Location_Frame:Hide() + end + end + else + -- MinimapZoneTextButton.Show = MiniMapWorldMapButton.Show + -- MinimapBorderTop.Show = MiniMapWorldMapButton.Show + -- MiniMapWorldMapButton.Show = MiniMapWorldMapButton.Show + + if ( IsAddOnLoaded("Chinchilla") ) then + if ( Chinchilla_Location_Frame and not Chinchilla_Location_Frame:IsShown() ) then + Chinchilla_Location_Frame:Show() + end + end + end +end + +function SLDT.ZoneText:Enable() + if ( db.enabled ) then + SLDT:UpdateBaseText(self, db) + self:RegisterEvent("ZONE_CHANGED") + self:RegisterEvent("ZONE_CHANGED_INDOORS") + self:RegisterEvent("ZONE_CHANGED_NEW_AREA") + self:SetScript("OnEvent", function() self:Refresh() end) + end + self:Refresh() +end + +function SLDT.ZoneText:Disable() + if ( not db.enabled ) then + self:UnregisterEvent("ZONE_CHANGED") + self:UnregisterEvent("ZONE_CHANGED_INDOORS") + self:UnregisterEvent("ZONE_CHANGED_NEW_AREA") + self:SetScript("OnEvent", nil) + end + self:Refresh() +end + +function SLDT.ZoneText:Refresh() + if ( db.enabled or SLDataText.db.profile.configMode ) then + if ( not self.firstRun ) then self.firstRun = true; SLDT:UpdateBaseText(self, db) end + + zoneName = GetZoneText() + subZoneName = GetSubZoneText() + pvpType, _, factionName = GetZonePVPInfo() + + if ( subZoneName == zoneName or subZoneName == "" ) then text:SetText(zoneName) else text:SetText(subZoneName) end + + if ( zCol[pvpType] ) then + text:SetTextColor(zCol[pvpType].r, zCol[pvpType].b, zCol[pvpType].g) + else + text:SetTextColor(1.0, 0.9294, 0.7607) + end + + SLDT:UpdateBaseFrame(self, db) + FixFrames(db.enabled) + else + if ( frame:IsShown() and not SLDataText.db.profile.configMode ) then frame:Hide() end + FixFrames(db.enabled) + end +end + +SLDT.ZoneText.optsTbl = { + [1] = { [1] = "toggle", [2] = L["Enabled"], [3] = "enabled" }, + [2] = { [1] = "toggle", [2] = L["Global Font"], [3] = "gfont" }, + [3] = { [1] = "toggle", [2] = L["Outline"], [3] = "outline" }, + [4] = { [1] = "toggle", [2] = L["Force Shown"], [3] = "forceShow" }, + [5] = { [1] = "toggle", [2] = L["Tooltip On"], [3] = "tooltipOn" }, + [6] = { [1] = "range", [2] = L["Font Size"], [3] = "fontSize", [4] = 6, [5] = 40, [6] = 1 }, + [7] = { [1] = "select", [2] = L["Font"], [3] = "font", [4] = SLDT.fontTbl }, + [8] = { [1] = "select", [2] = L["Justify"], [3] = "aP", [4] = SLDT.justTbl }, + [9] = { [1] = "text", [2] = L["Parent"], [3] = "anch" }, + [10] = { [1] = "select", [2] = L["Anchor"], [3] = "aF", [4] = SLDT.anchTbl }, + [11] = { [1] = "text", [2] = L["X Offset"], [3] = "xOff" }, + [12] = { [1] = "text", [2] = L["Y Offset"], [3] = "yOff" }, + [13] = { [1] = "select", [2] = L["Frame Strata"], [3] = "strata", [4] = SLDT.stratTbl }, +} + +local function OnInit() + SLDT.ZoneText.db = SLDT.db:RegisterNamespace(MODNAME) + SLDT.ZoneText.db:RegisterDefaults({ + profile = { + name = "ZoneText", + enabled = true, + forceShow = false, + aP = "CENTER", + anch = "Minimap", + aF = "BOTTOM", + xOff = 0, + yOff = -10, + strata = "LOW", + gfont = false, + fontSize = 14, + font = "Arial Narrow", + outline = false, + tooltipOn = true, + }, + }) + db = SLDT.ZoneText.db.profile + + SLDT.Modules = SLDT.Modules or {} + if ( not SLDT.Modules[MODNAME] ) then table.insert(SLDT.Modules, { MODNAME, db }) end + frame, text, tool = SLDT:SetupBaseFrame(SLDT.ZoneText) + SetupToolTip() + + SLDT.ZoneText:UnregisterEvent("PLAYER_ENTERING_WORLD") + SLDT.ZoneText:Enable() +end + +SLDT.ZoneText:RegisterEvent("PLAYER_ENTERING_WORLD") +SLDT.ZoneText:SetScript("OnEvent", OnInit) \ No newline at end of file diff --git a/Libs/AceDB-3.0/AceDB-3.0.lua b/Libs/AceDB-3.0/AceDB-3.0.lua new file mode 100644 index 0000000..9e84705 --- /dev/null +++ b/Libs/AceDB-3.0/AceDB-3.0.lua @@ -0,0 +1,740 @@ +--- **AceDB-3.0** manages the SavedVariables of your addon. +-- It offers profile management, smart defaults and namespaces for modules.\\ +-- Data can be saved in different data-types, depending on its intended usage. +-- The most common data-type is the `profile` type, which allows the user to choose +-- the active profile, and manage the profiles of all of his characters.\\ +-- The following data types are available: +-- * **char** Character-specific data. Every character has its own database. +-- * **realm** Realm-specific data. All of the players characters on the same realm share this database. +-- * **class** Class-specific data. All of the players characters of the same class share this database. +-- * **race** Race-specific data. All of the players characters of the same race share this database. +-- * **faction** Faction-specific data. All of the players characters of the same faction share this database. +-- * **factionrealm** Faction and realm specific data. All of the players characters on the same realm and of the same faction share this database. +-- * **locale** Locale specific data, based on the locale of the players game client. +-- * **global** Global Data. All characters on the same account share this database. +-- * **profile** Profile-specific data. All characters using the same profile share this database. The user can control which profile should be used. +-- +-- Creating a new Database using the `:New` function will return a new DBObject. A database will inherit all functions +-- of the DBObjectLib listed here. \\ +-- If you create a new namespaced child-database (`:RegisterNamespace`), you'll get a DBObject as well, but note +-- that the child-databases cannot individually change their profile, and are linked to their parents profile - and because of that, +-- the profile related APIs are not available. Only `:RegisterDefaults` and `:ResetProfile` are available on child-databases. +-- +-- For more details on how to use AceDB-3.0, see the [[AceDB-3.0 Tutorial]]. +-- +-- You may also be interested in [[libdualspec-1-0|LibDualSpec-1.0]] to do profile switching automatically when switching specs. +-- +-- @usage +-- MyAddon = LibStub("AceAddon-3.0"):NewAddon("DBExample") +-- +-- -- declare defaults to be used in the DB +-- local defaults = { +-- profile = { +-- setting = true, +-- } +-- } +-- +-- function MyAddon:OnInitialize() +-- -- Assuming the .toc says ## SavedVariables: MyAddonDB +-- self.db = LibStub("AceDB-3.0"):New("MyAddonDB", defaults, true) +-- end +-- @class file +-- @name AceDB-3.0.lua +-- @release $Id: AceDB-3.0.lua 1284 2022-09-25 09:15:30Z nevcairiel $ +local ACEDB_MAJOR, ACEDB_MINOR = "AceDB-3.0", 27 +local AceDB = LibStub:NewLibrary(ACEDB_MAJOR, ACEDB_MINOR) + +if not AceDB then return end -- No upgrade needed + +-- Lua APIs +local type, pairs, next, error = type, pairs, next, error +local setmetatable, rawset, rawget = setmetatable, rawset, rawget + +-- WoW APIs +local _G = _G + +AceDB.db_registry = AceDB.db_registry or {} +AceDB.frame = AceDB.frame or CreateFrame("Frame") + +local CallbackHandler +local CallbackDummy = { Fire = function() end } + +local DBObjectLib = {} + +--[[------------------------------------------------------------------------- + AceDB Utility Functions +---------------------------------------------------------------------------]] + +-- Simple shallow copy for copying defaults +local function copyTable(src, dest) + if type(dest) ~= "table" then dest = {} end + if type(src) == "table" then + for k,v in pairs(src) do + if type(v) == "table" then + -- try to index the key first so that the metatable creates the defaults, if set, and use that table + v = copyTable(v, dest[k]) + end + dest[k] = v + end + end + return dest +end + +-- Called to add defaults to a section of the database +-- +-- When a ["*"] default section is indexed with a new key, a table is returned +-- and set in the host table. These tables must be cleaned up by removeDefaults +-- in order to ensure we don't write empty default tables. +local function copyDefaults(dest, src) + -- this happens if some value in the SV overwrites our default value with a non-table + --if type(dest) ~= "table" then return end + for k, v in pairs(src) do + if k == "*" or k == "**" then + if type(v) == "table" then + -- This is a metatable used for table defaults + local mt = { + -- This handles the lookup and creation of new subtables + __index = function(t,k2) + if k2 == nil then return nil end + local tbl = {} + copyDefaults(tbl, v) + rawset(t, k2, tbl) + return tbl + end, + } + setmetatable(dest, mt) + -- handle already existing tables in the SV + for dk, dv in pairs(dest) do + if not rawget(src, dk) and type(dv) == "table" then + copyDefaults(dv, v) + end + end + else + -- Values are not tables, so this is just a simple return + local mt = {__index = function(t,k2) return k2~=nil and v or nil end} + setmetatable(dest, mt) + end + elseif type(v) == "table" then + if not rawget(dest, k) then rawset(dest, k, {}) end + if type(dest[k]) == "table" then + copyDefaults(dest[k], v) + if src['**'] then + copyDefaults(dest[k], src['**']) + end + end + else + if rawget(dest, k) == nil then + rawset(dest, k, v) + end + end + end +end + +-- Called to remove all defaults in the default table from the database +local function removeDefaults(db, defaults, blocker) + -- remove all metatables from the db, so we don't accidentally create new sub-tables through them + setmetatable(db, nil) + -- loop through the defaults and remove their content + for k,v in pairs(defaults) do + if k == "*" or k == "**" then + if type(v) == "table" then + -- Loop through all the actual k,v pairs and remove + for key, value in pairs(db) do + if type(value) == "table" then + -- if the key was not explicitly specified in the defaults table, just strip everything from * and ** tables + if defaults[key] == nil and (not blocker or blocker[key] == nil) then + removeDefaults(value, v) + -- if the table is empty afterwards, remove it + if next(value) == nil then + db[key] = nil + end + -- if it was specified, only strip ** content, but block values which were set in the key table + elseif k == "**" then + removeDefaults(value, v, defaults[key]) + end + end + end + elseif k == "*" then + -- check for non-table default + for key, value in pairs(db) do + if defaults[key] == nil and v == value then + db[key] = nil + end + end + end + elseif type(v) == "table" and type(db[k]) == "table" then + -- if a blocker was set, dive into it, to allow multi-level defaults + removeDefaults(db[k], v, blocker and blocker[k]) + if next(db[k]) == nil then + db[k] = nil + end + else + -- check if the current value matches the default, and that its not blocked by another defaults table + if db[k] == defaults[k] and (not blocker or blocker[k] == nil) then + db[k] = nil + end + end + end +end + +-- This is called when a table section is first accessed, to set up the defaults +local function initSection(db, section, svstore, key, defaults) + local sv = rawget(db, "sv") + + local tableCreated + if not sv[svstore] then sv[svstore] = {} end + if not sv[svstore][key] then + sv[svstore][key] = {} + tableCreated = true + end + + local tbl = sv[svstore][key] + + if defaults then + copyDefaults(tbl, defaults) + end + rawset(db, section, tbl) + + return tableCreated, tbl +end + +-- Metatable to handle the dynamic creation of sections and copying of sections. +local dbmt = { + __index = function(t, section) + local keys = rawget(t, "keys") + local key = keys[section] + if key then + local defaultTbl = rawget(t, "defaults") + local defaults = defaultTbl and defaultTbl[section] + + if section == "profile" then + local new = initSection(t, section, "profiles", key, defaults) + if new then + -- Callback: OnNewProfile, database, newProfileKey + t.callbacks:Fire("OnNewProfile", t, key) + end + elseif section == "profiles" then + local sv = rawget(t, "sv") + if not sv.profiles then sv.profiles = {} end + rawset(t, "profiles", sv.profiles) + elseif section == "global" then + local sv = rawget(t, "sv") + if not sv.global then sv.global = {} end + if defaults then + copyDefaults(sv.global, defaults) + end + rawset(t, section, sv.global) + else + initSection(t, section, section, key, defaults) + end + end + + return rawget(t, section) + end +} + +local function validateDefaults(defaults, keyTbl, offset) + if not defaults then return end + offset = offset or 0 + for k in pairs(defaults) do + if not keyTbl[k] or k == "profiles" then + error(("Usage: AceDBObject:RegisterDefaults(defaults): '%s' is not a valid datatype."):format(k), 3 + offset) + end + end +end + +local preserve_keys = { + ["callbacks"] = true, + ["RegisterCallback"] = true, + ["UnregisterCallback"] = true, + ["UnregisterAllCallbacks"] = true, + ["children"] = true, +} + +local realmKey = GetRealmName() +local charKey = UnitName("player") .. " - " .. realmKey +local _, classKey = UnitClass("player") +local _, raceKey = UnitRace("player") +local factionKey = UnitFactionGroup("player") +local factionrealmKey = factionKey .. " - " .. realmKey +local localeKey = GetLocale():lower() + +local regionTable = { "US", "KR", "EU", "TW", "CN" } +local regionKey = regionTable[GetCurrentRegion()] +local factionrealmregionKey = factionrealmKey .. " - " .. regionKey + +-- Actual database initialization function +local function initdb(sv, defaults, defaultProfile, olddb, parent) + -- Generate the database keys for each section + + -- map "true" to our "Default" profile + if defaultProfile == true then defaultProfile = "Default" end + + local profileKey + if not parent then + -- Make a container for profile keys + if not sv.profileKeys then sv.profileKeys = {} end + + -- Try to get the profile selected from the char db + profileKey = sv.profileKeys[charKey] or defaultProfile or charKey + + -- save the selected profile for later + sv.profileKeys[charKey] = profileKey + else + -- Use the profile of the parents DB + profileKey = parent.keys.profile or defaultProfile or charKey + + -- clear the profileKeys in the DB, namespaces don't need to store them + sv.profileKeys = nil + end + + -- This table contains keys that enable the dynamic creation + -- of each section of the table. The 'global' and 'profiles' + -- have a key of true, since they are handled in a special case + local keyTbl= { + ["char"] = charKey, + ["realm"] = realmKey, + ["class"] = classKey, + ["race"] = raceKey, + ["faction"] = factionKey, + ["factionrealm"] = factionrealmKey, + ["factionrealmregion"] = factionrealmregionKey, + ["profile"] = profileKey, + ["locale"] = localeKey, + ["global"] = true, + ["profiles"] = true, + } + + validateDefaults(defaults, keyTbl, 1) + + -- This allows us to use this function to reset an entire database + -- Clear out the old database + if olddb then + for k,v in pairs(olddb) do if not preserve_keys[k] then olddb[k] = nil end end + end + + -- Give this database the metatable so it initializes dynamically + local db = setmetatable(olddb or {}, dbmt) + + if not rawget(db, "callbacks") then + -- try to load CallbackHandler-1.0 if it loaded after our library + if not CallbackHandler then CallbackHandler = LibStub:GetLibrary("CallbackHandler-1.0", true) end + db.callbacks = CallbackHandler and CallbackHandler:New(db) or CallbackDummy + end + + -- Copy methods locally into the database object, to avoid hitting + -- the metatable when calling methods + + if not parent then + for name, func in pairs(DBObjectLib) do + db[name] = func + end + else + -- hack this one in + db.RegisterDefaults = DBObjectLib.RegisterDefaults + db.ResetProfile = DBObjectLib.ResetProfile + end + + -- Set some properties in the database object + db.profiles = sv.profiles + db.keys = keyTbl + db.sv = sv + --db.sv_name = name + db.defaults = defaults + db.parent = parent + + -- store the DB in the registry + AceDB.db_registry[db] = true + + return db +end + +-- handle PLAYER_LOGOUT +-- strip all defaults from all databases +-- and cleans up empty sections +local function logoutHandler(frame, event) + if event == "PLAYER_LOGOUT" then + for db in pairs(AceDB.db_registry) do + db.callbacks:Fire("OnDatabaseShutdown", db) + db:RegisterDefaults(nil) + + -- cleanup sections that are empty without defaults + local sv = rawget(db, "sv") + for section in pairs(db.keys) do + if rawget(sv, section) then + -- global is special, all other sections have sub-entrys + -- also don't delete empty profiles on main dbs, only on namespaces + if section ~= "global" and (section ~= "profiles" or rawget(db, "parent")) then + for key in pairs(sv[section]) do + if not next(sv[section][key]) then + sv[section][key] = nil + end + end + end + if not next(sv[section]) then + sv[section] = nil + end + end + end + end + end +end + +AceDB.frame:RegisterEvent("PLAYER_LOGOUT") +AceDB.frame:SetScript("OnEvent", logoutHandler) + + +--[[------------------------------------------------------------------------- + AceDB Object Method Definitions +---------------------------------------------------------------------------]] + +--- Sets the defaults table for the given database object by clearing any +-- that are currently set, and then setting the new defaults. +-- @param defaults A table of defaults for this database +function DBObjectLib:RegisterDefaults(defaults) + if defaults and type(defaults) ~= "table" then + error(("Usage: AceDBObject:RegisterDefaults(defaults): 'defaults' - table or nil expected, got %q."):format(type(defaults)), 2) + end + + validateDefaults(defaults, self.keys) + + -- Remove any currently set defaults + if self.defaults then + for section,key in pairs(self.keys) do + if self.defaults[section] and rawget(self, section) then + removeDefaults(self[section], self.defaults[section]) + end + end + end + + -- Set the DBObject.defaults table + self.defaults = defaults + + -- Copy in any defaults, only touching those sections already created + if defaults then + for section,key in pairs(self.keys) do + if defaults[section] and rawget(self, section) then + copyDefaults(self[section], defaults[section]) + end + end + end +end + +--- Changes the profile of the database and all of it's namespaces to the +-- supplied named profile +-- @param name The name of the profile to set as the current profile +function DBObjectLib:SetProfile(name) + if type(name) ~= "string" then + error(("Usage: AceDBObject:SetProfile(name): 'name' - string expected, got %q."):format(type(name)), 2) + end + + -- changing to the same profile, dont do anything + if name == self.keys.profile then return end + + local oldProfile = self.profile + local defaults = self.defaults and self.defaults.profile + + -- Callback: OnProfileShutdown, database + self.callbacks:Fire("OnProfileShutdown", self) + + if oldProfile and defaults then + -- Remove the defaults from the old profile + removeDefaults(oldProfile, defaults) + end + + self.profile = nil + self.keys["profile"] = name + + -- if the storage exists, save the new profile + -- this won't exist on namespaces. + if self.sv.profileKeys then + self.sv.profileKeys[charKey] = name + end + + -- populate to child namespaces + if self.children then + for _, db in pairs(self.children) do + DBObjectLib.SetProfile(db, name) + end + end + + -- Callback: OnProfileChanged, database, newProfileKey + self.callbacks:Fire("OnProfileChanged", self, name) +end + +--- Returns a table with the names of the existing profiles in the database. +-- You can optionally supply a table to re-use for this purpose. +-- @param tbl A table to store the profile names in (optional) +function DBObjectLib:GetProfiles(tbl) + if tbl and type(tbl) ~= "table" then + error(("Usage: AceDBObject:GetProfiles(tbl): 'tbl' - table or nil expected, got %q."):format(type(tbl)), 2) + end + + -- Clear the container table + if tbl then + for k,v in pairs(tbl) do tbl[k] = nil end + else + tbl = {} + end + + local curProfile = self.keys.profile + + local i = 0 + for profileKey in pairs(self.profiles) do + i = i + 1 + tbl[i] = profileKey + if curProfile and profileKey == curProfile then curProfile = nil end + end + + -- Add the current profile, if it hasn't been created yet + if curProfile then + i = i + 1 + tbl[i] = curProfile + end + + return tbl, i +end + +--- Returns the current profile name used by the database +function DBObjectLib:GetCurrentProfile() + return self.keys.profile +end + +--- Deletes a named profile. This profile must not be the active profile. +-- @param name The name of the profile to be deleted +-- @param silent If true, do not raise an error when the profile does not exist +function DBObjectLib:DeleteProfile(name, silent) + if type(name) ~= "string" then + error(("Usage: AceDBObject:DeleteProfile(name): 'name' - string expected, got %q."):format(type(name)), 2) + end + + if self.keys.profile == name then + error(("Cannot delete the active profile (%q) in an AceDBObject."):format(name), 2) + end + + if not rawget(self.profiles, name) and not silent then + error(("Cannot delete profile %q as it does not exist."):format(name), 2) + end + + self.profiles[name] = nil + + -- populate to child namespaces + if self.children then + for _, db in pairs(self.children) do + DBObjectLib.DeleteProfile(db, name, true) + end + end + + -- switch all characters that use this profile back to the default + if self.sv.profileKeys then + for key, profile in pairs(self.sv.profileKeys) do + if profile == name then + self.sv.profileKeys[key] = nil + end + end + end + + -- Callback: OnProfileDeleted, database, profileKey + self.callbacks:Fire("OnProfileDeleted", self, name) +end + +--- Copies a named profile into the current profile, overwriting any conflicting +-- settings. +-- @param name The name of the profile to be copied into the current profile +-- @param silent If true, do not raise an error when the profile does not exist +function DBObjectLib:CopyProfile(name, silent) + if type(name) ~= "string" then + error(("Usage: AceDBObject:CopyProfile(name): 'name' - string expected, got %q."):format(type(name)), 2) + end + + if name == self.keys.profile then + error(("Cannot have the same source and destination profiles (%q)."):format(name), 2) + end + + if not rawget(self.profiles, name) and not silent then + error(("Cannot copy profile %q as it does not exist."):format(name), 2) + end + + -- Reset the profile before copying + DBObjectLib.ResetProfile(self, nil, true) + + local profile = self.profile + local source = self.profiles[name] + + copyTable(source, profile) + + -- populate to child namespaces + if self.children then + for _, db in pairs(self.children) do + DBObjectLib.CopyProfile(db, name, true) + end + end + + -- Callback: OnProfileCopied, database, sourceProfileKey + self.callbacks:Fire("OnProfileCopied", self, name) +end + +--- Resets the current profile to the default values (if specified). +-- @param noChildren if set to true, the reset will not be populated to the child namespaces of this DB object +-- @param noCallbacks if set to true, won't fire the OnProfileReset callback +function DBObjectLib:ResetProfile(noChildren, noCallbacks) + local profile = self.profile + + for k,v in pairs(profile) do + profile[k] = nil + end + + local defaults = self.defaults and self.defaults.profile + if defaults then + copyDefaults(profile, defaults) + end + + -- populate to child namespaces + if self.children and not noChildren then + for _, db in pairs(self.children) do + DBObjectLib.ResetProfile(db, nil, noCallbacks) + end + end + + -- Callback: OnProfileReset, database + if not noCallbacks then + self.callbacks:Fire("OnProfileReset", self) + end +end + +--- Resets the entire database, using the string defaultProfile as the new default +-- profile. +-- @param defaultProfile The profile name to use as the default +function DBObjectLib:ResetDB(defaultProfile) + if defaultProfile and type(defaultProfile) ~= "string" then + error(("Usage: AceDBObject:ResetDB(defaultProfile): 'defaultProfile' - string or nil expected, got %q."):format(type(defaultProfile)), 2) + end + + local sv = self.sv + for k,v in pairs(sv) do + sv[k] = nil + end + + initdb(sv, self.defaults, defaultProfile, self) + + -- fix the child namespaces + if self.children then + if not sv.namespaces then sv.namespaces = {} end + for name, db in pairs(self.children) do + if not sv.namespaces[name] then sv.namespaces[name] = {} end + initdb(sv.namespaces[name], db.defaults, self.keys.profile, db, self) + end + end + + -- Callback: OnDatabaseReset, database + self.callbacks:Fire("OnDatabaseReset", self) + -- Callback: OnProfileChanged, database, profileKey + self.callbacks:Fire("OnProfileChanged", self, self.keys["profile"]) + + return self +end + +--- Creates a new database namespace, directly tied to the database. This +-- is a full scale database in it's own rights other than the fact that +-- it cannot control its profile individually +-- @param name The name of the new namespace +-- @param defaults A table of values to use as defaults +function DBObjectLib:RegisterNamespace(name, defaults) + if type(name) ~= "string" then + error(("Usage: AceDBObject:RegisterNamespace(name, defaults): 'name' - string expected, got %q."):format(type(name)), 2) + end + if defaults and type(defaults) ~= "table" then + error(("Usage: AceDBObject:RegisterNamespace(name, defaults): 'defaults' - table or nil expected, got %q."):format(type(defaults)), 2) + end + if self.children and self.children[name] then + error(("Usage: AceDBObject:RegisterNamespace(name, defaults): 'name' - a namespace called %q already exists."):format(name), 2) + end + + local sv = self.sv + if not sv.namespaces then sv.namespaces = {} end + if not sv.namespaces[name] then + sv.namespaces[name] = {} + end + + local newDB = initdb(sv.namespaces[name], defaults, self.keys.profile, nil, self) + + if not self.children then self.children = {} end + self.children[name] = newDB + return newDB +end + +--- Returns an already existing namespace from the database object. +-- @param name The name of the new namespace +-- @param silent if true, the addon is optional, silently return nil if its not found +-- @usage +-- local namespace = self.db:GetNamespace('namespace') +-- @return the namespace object if found +function DBObjectLib:GetNamespace(name, silent) + if type(name) ~= "string" then + error(("Usage: AceDBObject:GetNamespace(name): 'name' - string expected, got %q."):format(type(name)), 2) + end + if not silent and not (self.children and self.children[name]) then + error(("Usage: AceDBObject:GetNamespace(name): 'name' - namespace %q does not exist."):format(name), 2) + end + if not self.children then self.children = {} end + return self.children[name] +end + +--[[------------------------------------------------------------------------- + AceDB Exposed Methods +---------------------------------------------------------------------------]] + +--- Creates a new database object that can be used to handle database settings and profiles. +-- By default, an empty DB is created, using a character specific profile. +-- +-- You can override the default profile used by passing any profile name as the third argument, +-- or by passing //true// as the third argument to use a globally shared profile called "Default". +-- +-- Note that there is no token replacement in the default profile name, passing a defaultProfile as "char" +-- will use a profile named "char", and not a character-specific profile. +-- @param tbl The name of variable, or table to use for the database +-- @param defaults A table of database defaults +-- @param defaultProfile The name of the default profile. If not set, a character specific profile will be used as the default. +-- You can also pass //true// to use a shared global profile called "Default". +-- @usage +-- -- Create an empty DB using a character-specific default profile. +-- self.db = LibStub("AceDB-3.0"):New("MyAddonDB") +-- @usage +-- -- Create a DB using defaults and using a shared default profile +-- self.db = LibStub("AceDB-3.0"):New("MyAddonDB", defaults, true) +function AceDB:New(tbl, defaults, defaultProfile) + if type(tbl) == "string" then + local name = tbl + tbl = _G[name] + if not tbl then + tbl = {} + _G[name] = tbl + end + end + + if type(tbl) ~= "table" then + error(("Usage: AceDB:New(tbl, defaults, defaultProfile): 'tbl' - table expected, got %q."):format(type(tbl)), 2) + end + + if defaults and type(defaults) ~= "table" then + error(("Usage: AceDB:New(tbl, defaults, defaultProfile): 'defaults' - table expected, got %q."):format(type(defaults)), 2) + end + + if defaultProfile and type(defaultProfile) ~= "string" and defaultProfile ~= true then + error(("Usage: AceDB:New(tbl, defaults, defaultProfile): 'defaultProfile' - string or true expected, got %q."):format(type(defaultProfile)), 2) + end + + return initdb(tbl, defaults, defaultProfile) +end + +-- upgrade existing databases +for db in pairs(AceDB.db_registry) do + if not db.parent then + for name,func in pairs(DBObjectLib) do + db[name] = func + end + else + db.RegisterDefaults = DBObjectLib.RegisterDefaults + db.ResetProfile = DBObjectLib.ResetProfile + end +end diff --git a/Libs/AceDB-3.0/AceDB-3.0.xml b/Libs/AceDB-3.0/AceDB-3.0.xml new file mode 100644 index 0000000..28998e5 --- /dev/null +++ b/Libs/AceDB-3.0/AceDB-3.0.xml @@ -0,0 +1,4 @@ + +