You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

272 lines
9.7 KiB

-- Neuron is a World of Warcraft® user interface addon.
-- Copyright (c) 2017-2021 Britt W. Yazel
-- Copyright (c) 2006-2014 Connor H. Chenoweth
-- This code is licensed under the MIT license (see LICENSE for details)
local _, addonTable = ...
local Neuron = addonTable.Neuron
---@class ExpButton: StatusButton @define class ExpButton inherits from class StatusButton
local ExpButton = setmetatable({}, { __index = Neuron.StatusButton })
Neuron.ExpButton = ExpButton
local L = LibStub("AceLocale-3.0"):GetLocale("Neuron")
ExpButton.sbStrings = {
[1] = { L["None"], function(self) return "" end },
[2] = { L["Current/Next"], function(self) if self.current and self.next then return BreakUpLargeNumbers(self.current).." / "..BreakUpLargeNumbers(self.next) end end },
[3] = { L["Rested Levels"], function(self) if self.rested then return string.format("%.2f", tostring(self.rested)).." "..L["Levels"] end end },
[4] = { L["Percent"], function(self) if self.percent then return string.format("%.2f", tostring(self.percent)).."%" end end },
[5] = { L["Bubbles"], function(self) if self.bubbles then return tostring(self.bubbles).." / 20 "..L["Bubbles"] end end},
[6] = { L["Current Level/Rank"], function(self) if self.rank then return L["Level"].." "..tostring(self.rank) end end },
}
---Constructor: Create a new Neuron Button object (this is the base object for all Neuron button types)
---@param bar Bar @Bar Object this button will be a child of
---@param buttonID number @Button ID that this button will be assigned
---@param defaults table @Default options table to be loaded onto the given button
---@return ExpButton @ A newly created StatusButton object
function ExpButton.new(bar, buttonID, defaults)
--call the parent object constructor with the provided information specific to this button type
local newButton = Neuron.StatusButton.new(bar, buttonID, defaults, ExpButton, "XPBar", "XP Button")
return newButton
end
function ExpButton:InitializeButton()
self:SetAttribute("hasaction", true)
self:RegisterForClicks("RightButtonUp")
self:SetScript("OnClick", function(_, mousebutton) self:OnClick(mousebutton) end)
self:SetScript("OnEnter", function() self:OnEnter() end)
self:SetScript("OnLeave", function() self:OnLeave() end)
self:SetHitRectInsets(0, 0, 0, 0)
self:RegisterEvent("PLAYER_XP_UPDATE", "OnEvent")
self:RegisterEvent("UPDATE_EXHAUSTION", "OnEvent")
self:RegisterEvent("PLAYER_ENTERING_WORLD", "OnEvent")
self:RegisterEvent("PLAYER_EQUIPMENT_CHANGED", "OnEvent")
if Neuron.isWoWRetail then
self:RegisterEvent("COVENANT_SANCTUM_RENOWN_LEVEL_CHANGED", "OnEvent")
self:RegisterEvent("AZERITE_ITEM_EXPERIENCE_CHANGED", "OnEvent")
self:RegisterEvent("HONOR_XP_UPDATE", "OnEvent")
end
self.StatusBar:Show()
self.typeString = L["XP Bar"]
self:InitializeButtonSettings()
end
---TODO: right now we are using DB.statusbtn to assign settings ot the status buttons, but I think our indexes are bar specific
function ExpButton:UpdateData() --handles updating all the strings for the play XP watch bar
--player xp option
if self:GetXPType() == "player_xp" then
self.current, self.next, self.rested = UnitXP("player"), UnitXPMax("player"), GetXPExhaustion()
self.rank = UnitLevel("player")
--at max level we want to show the bar as full, so just max out the current XP
if self.rank == MAX_PLAYER_LEVEL then
self.current = self.next
end
self.percent = (self.current/self.next)*100
self.bubbles = math.floor(self.percent/5)
if self.rested then
self.rested = self.rested/self.next
else
self.rested = 0
end
--covenant renown
elseif self:GetXPType() == "covenant_renown" then
if C_Covenants.GetActiveCovenantID() ~= 0 then
local covenantLevel = C_CovenantSanctumUI.GetRenownLevel(C_Covenants.GetActiveCovenantID())
local covenantName = C_Covenants.GetCovenantData(C_Covenants.GetActiveCovenantID()).name
self.rank = covenantName..": "..L["Level"].." "..covenantLevel
self.rested = 0
self.percent = 100
self.bubbles = 20
self.current = 100
self.next = 100
else
self.current = 0
self.next = 0
self.percent = 0
self.rested = 0
self.bubbles = 0
self.rank = 0
end
--heart of azeroth option
elseif self:GetXPType() == "azerite_xp" then
local azeriteItemLocation = C_AzeriteItem.FindActiveAzeriteItem()
if azeriteItemLocation then
self.current, self.next = C_AzeriteItem.GetAzeriteItemXPInfo(azeriteItemLocation)
self.rested = 0
self.percent = (self.current/self.next)*100
self.bubbles = math.floor(self.percent/5)
self.rank = C_AzeriteItem.GetPowerLevel(azeriteItemLocation)
else
self.current = 0
self.next = 0
self.percent = 0
self.rested = 0
self.bubbles = 0
self.rank = 0
end
--honor points option
elseif self:GetXPType() == "honor_points" then
self.current = UnitHonor("player"); -- current value for level
self.next = UnitHonorMax("player"); -- max value for level
self.rested = 0
self.rank = UnitHonorLevel("player");
self.percent = (self.current/self.next)*100
self.bubbles = math.floor(self.percent/5)
end
end
function ExpButton:OnEvent(event)
self:UpdateData()
if self:GetXPType() == "player_xp" and (event=="PLAYER_XP_UPDATE" or event =="PLAYER_ENTERING_WORLD" or event=="UPDATE_EXHAUSTION" or event =="changed_curXPType") then
if self.rested ~= 0 or UnitLevel("player") == MAX_PLAYER_LEVEL then
self.StatusBar:SetStatusBarColor(0.0, 0.39, 0.88, 1.0) --blue color
else
self.StatusBar:SetStatusBarColor(0.58, 0.0, 0.55, 1.0) --deep purple color
end
elseif self:GetXPType() == "covenant_renown" and (event == "COVENANT_SANCTUM_RENOWN_LEVEL_CHANGED" or event =="PLAYER_ENTERING_WORLD" or event =="changed_curXPType") then
local covenantData = C_Covenants.GetCovenantData(C_Covenants.GetActiveCovenantID())
local covenantColor = COVENANT_COLORS[covenantData.textureKit]
self.StatusBar:SetStatusBarColor(covenantColor:GetRGB())
elseif self:GetXPType() == "azerite_xp" and (event =="AZERITE_ITEM_EXPERIENCE_CHANGED" or event =="PLAYER_ENTERING_WORLD" or event =="PLAYER_EQUIPMENT_CHANGED" or event =="changed_curXPType") then
self.StatusBar:SetStatusBarColor(ARTIFACT_BAR_COLOR:GetRGB()) --set to pale yellow
elseif self:GetXPType() == "honor_points" and (event=="HONOR_XP_UPDATE" or event =="PLAYER_ENTERING_WORLD" or event =="changed_curXPType") then
self.StatusBar:SetStatusBarColor(1.0, 0.24, 0) --set to red
end
self.StatusBar:SetMinMaxValues(0, 100) --these are for the bar itself, the progress it has from left to right
self.StatusBar:SetValue((self.current/self.next)*100)
self.StatusBar.CenterText:SetText(self:cFunc())
self.StatusBar.LeftText:SetText(self:lFunc())
self.StatusBar.RightText:SetText(self:rFunc())
self.StatusBar.MouseoverText:SetText(self:mFunc())
end
function ExpButton:InitializeDropDown() -- initialize the dropdown menu for chosing to watch either XP, azerite XP, or Honor Points
--this is the frame that will hold our dropdown menu
local menuFrame
if not NeuronXPDropdownMenu then --try to avoid re-creating this over again if we don't have to
menuFrame = CreateFrame("Frame", "NeuronXPDropdownMenu", self, "UIDropDownMenuTemplate")
else
menuFrame = NeuronXPDropdownMenu
end
menuFrame:SetPoint("BOTTOMLEFT", self, "TOPRIGHT", 0, 0)
local menu = {}
-- Menu Title
table.insert(menu, {text = L["Select an Option"], isTitle = true, notCheckable=true, justifyH = "CENTER",})
--add Player XP option
table.insert(menu, {
arg1 = self,
arg2 = "player_xp",
text = L["Track Character XP"],
func = function(dropdown, self, newXPType) self:SetXPType(newXPType) end,
checked = self:GetXPType() == "player_xp",
})
--wow classic doesn't have Honor points nor Azerite, careful
if Neuron.isWoWRetail then
--add Renown tracking for Covenants
if C_Covenants.GetActiveCovenantID() ~= 0 then
table.insert(menu, {
arg1 = self,
arg2 = "covenant_renown",
text = L["Track Covenant Renown"],
func = function(dropdown, self, newXPType) self:SetXPType(newXPType) end,
checked = self:GetXPType() == "covenant_renown",
})
end
--add Heart of Azeroth option
local azeriteItem = C_AzeriteItem.FindActiveAzeriteItem()
if azeriteItem and azeriteItem:IsEquipmentSlot() and C_AzeriteItem.IsAzeriteItemEnabled(azeriteItem) then --only show this button if they player has the Heart of Azeroth
table.insert(menu, {
arg1 = self,
arg2 = "azerite_xp",
text = L["Track Azerite Power"],
func = function(dropdown, self, newXPType) self:SetXPType(newXPType) end,
checked = self:GetXPType() == "azerite_xp",
})
end
--add PvP Honor option
table.insert(menu, {
arg1 = self,
arg2 = "honor_points",
text = L["Track Honor Points"],
func = function(dropdown, self, newXPType) self:SetXPType(newXPType) end,
checked = self:GetXPType() == "honor_points",
})
end
--this is a spacer between everything else and close
table.insert(menu, {
arg1=nil,
arg2=nil,
text=" ",
disabled=true,
func=function() end,
value=nil,
checked=nil,
justifyH = "CENTER",
notCheckable=true
})
--close button in case you don't want to change
table.insert(menu, {
arg1=self,
arg2=nil,
text=L["Close"],
func= function() --self is arg1
menuFrame:Hide()
end,
notCheckable = true,
justifyH = "CENTER",
})
--build the EasyMenu with the newly created menu table "menu"
EasyMenu(menu, menuFrame, "cursor", 0 , 0, "MENU", 1)
end
function ExpButton:OnClick(mousebutton)
if (mousebutton == "RightButton") then
self:InitializeDropDown()
end
end
-----------------------------------------------------
-------------------Sets and Gets---------------------
-----------------------------------------------------
function ExpButton:SetXPType(newXPType)
self.config.curXPType = newXPType
self:OnEvent("changed_curXPType")
end
function ExpButton:GetXPType()
return self.config.curXPType
end