Mercurial > wow > reaction
diff classes/ReAction_ActionDisplay.lua @ 7:f920db5fc6b1
version 0.3
author | Flick <flickerstreak@gmail.com> |
---|---|
date | Tue, 20 Mar 2007 21:25:29 +0000 |
parents | |
children | c05fd3e18b4f |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/classes/ReAction_ActionDisplay.lua Tue Mar 20 21:25:29 2007 +0000 @@ -0,0 +1,391 @@ +-- The ReAction.ActionDisplay mixin defines 'regular' action button display functionality +-- and is an implementation of the ReAction.IDisplay and ReAction.ActionType.IDisplay interfaces. +-- +-- This Mixin assumes that it has been mixed in with a ReAction-derived class which implements +-- the ReAction.IActionType and ReAction.IColorScheme interfaces. +-- +-- This mixin uses properties of self.config to define display elements: +-- +-- self.config = { +-- keyBindLoc = "POSITION", -- keybind anchor location +-- stackCountLoc = "POSITION", -- stack count anchor location +-- showKeyBind = true/false, -- show keybind labels +-- showStackCount = true/false, -- show stack count labels +-- showMacroText = true/false, -- show macro name labels +-- showGrid = true/false, -- always show empty buttons +-- } +-- + +local AceOO = AceLibrary("AceOO-2.0") + +ReAction.ActionDisplay = AceOO.Mixin { + -- ReAction.IDisplay interface + "SetupDisplay", + "UpdateDisplay", + "TempShow", + "GetActionFrame", + "GetBaseButtonSize", + "DisplayID", + "DisplayHotkey", + + -- ReAction.ActionType.IDisplay interface + "DisplayUsable", + "DisplayEquipped", + "DisplayAutoRepeat", + "DisplayInUse", + "DisplayIcon", + "DisplayName", + "DisplayCount", + "DisplayCooldown", + + -- Event handlers + "PostClick", + "OnDragStart", + "OnReceiveDrag", + "OnEnter", + "OnLeave", + "OnUpdate", + + -- internal functions + "ApplyLayout", + "ApplyStyle", + "StartFlash", + "StopFlash", + "IsFlashing", + "DisplayVisibility", +} + +local RAAD = ReAction.ActionDisplay + + +-- private constants +local _G = getfenv(0) + +local equippedActionBorderColor = { r=0.00, g=1.00, b=0.00, a=0.35 } -- transparent green +local actionIDColor = { r=1.00, g=0.82, b=0.00, a=1.00 } -- gold + +-- private functions +-- extract and return color fields from a table, to be fed into SetVertexColor()/SetTextColor() +local function tcolor(c) + return c.r, c.g, c.b, c.a +end + + +----------------------------------- +-- Interface Implementation Methods +----------------------------------- +function RAAD:SetupDisplay( name ) + -- create the button widget + local b = CreateFrame("CheckButton", name, nil, "SecureActionButtonTemplate, ActionButtonTemplate") + + -- store references to the various sub-frames of ActionButtonTemplate so we don't have to look it up all the time + self.frames = { + button = b, + hotkey = _G[name.."HotKey"], + count = _G[name.."Count"], + cooldown = _G[name.."Cooldown"], + macro = _G[name.."Name"], + icon = _G[name.."Icon"], + border = _G[name.."Border"], + flash = _G[name.."Flash"], + normalTexture = _G[name.."NormalTexture"], + actionID = nil, -- defer creating actionID font string until it's actually requested + } + + -- ??? odd: why do we have to increment the cooldown frame level to get it to show? + -- (otherwise it's behind the icon). The default UI doesn't have to (or at least I can't + -- find where it does) but for some reason we have to here. + self.frames.cooldown:SetFrameLevel(self.frames.cooldown:GetFrameLevel() + 1) + + b:EnableMouse() + b:RegisterForDrag("LeftButton", "RightButton") + b:RegisterForClicks("AnyUp") + b:SetScript("PostClick", function(arg1) self:PostClick(arg1) end) + b:SetScript("OnDragStart", function(arg1) self:OnDragStart(arg1) end) + b:SetScript("OnReceiveDrag", function() self:OnReceiveDrag() end) + b:SetScript("OnEnter", function() self:OnEnter() end) + b:SetScript("OnLeave", function() self:OnLeave() end) + -- defer setting OnUpdate until actions are actually attached + + self.tmpShow_ = 0 +end + +function RAAD:UpdateDisplay() + self:ApplyLayout() + self:ApplyStyle() + self:DisplayVisibility() + -- refresh the action ID display + if ReAction.showIDs_ then + self:DisplayID(self:GetID()) + end +end + +function RAAD:TempShow( visible ) + visible = visible and true or false -- force data integrity + self.showTmp_ = max(0, (self.showTmp_ or 0) + (visible and 1 or -1)) + self:DisplayVisibility() +end + +function RAAD:GetActionFrame() + return self.frames.button +end + +function RAAD:GetBaseButtonSize() + return 36 +end + +function RAAD:DisplayID( id ) + local f = self.frames.actionID + if id then + if not f then + -- create the actionID label + f = self.frames.button:CreateFontString(nil,"ARTWORK","NumberFontNormalSmall") + f:SetPoint("BOTTOMLEFT") + f:SetTextColor( tcolor(actionIDColor) ) + self.frames.actionID = f + end + f:SetText(tostring(id)) + f:Show() + elseif f then + f:Hide() + end +end + +function RAAD:DisplayHotkey(txt) + self.frames.hotkey:SetText(string.upper(txt or "")) + self:UpdateUsable() +end + +function RAAD:DisplayUsable( isUsable, notEnoughMana, outOfRange ) + local f = self.frames + f.icon:SetVertexColor( self:GetIconColor(isUsable, notEnoughMana, outOfRange) ) + f.button:GetNormalTexture():SetVertexColor( self:GetBorderColor(isUsable, notEnoughMana, outOfRange) ) + f.hotkey:SetTextColor( self:GetHotkeyColor(isUsable, notEnoughMana, outOfRange, f.hotkey:GetText()) ) +end + +function RAAD:DisplayEquipped( equipped ) + local b = self.frames.border + if equipped then + b:Show() + else + b:Hide() + end +end + +function RAAD:DisplayAutoRepeat( r ) + if r then + self:StartFlash() + else + self:StopFlash() + end +end + +function RAAD:DisplayInUse( inUse ) + self.frames.button:SetChecked( inUse and 1 or 0 ) +end + +function RAAD:DisplayIcon( texture ) + local f = self.frames.button + local icon = self.frames.icon + if texture then + icon:SetTexture(texture) + icon:Show() + self.rangeTimer = -1 + f:SetNormalTexture("Interface\\Buttons\\UI-Quickslot2") + if f:GetScript("OnUpdate") == nil then + f:SetScript("OnUpdate", function(frame, elapsed) self:OnUpdate(elapsed) end) + end + else + icon:Hide() + self.rangeTimer = nil + f:SetNormalTexture("Interface\\Buttons\\UI-Quickslot") + f:SetScript("OnUpdate",nil) + end + self:DisplayVisibility() +end + +function RAAD:DisplayCooldown( start, duration, enable ) + CooldownFrame_SetTimer(self.frames.cooldown, start, duration, enable) +end + +function RAAD:DisplayName( name ) + self.frames.macro:SetText(name and tostring(name) or "") +end + +function RAAD:DisplayCount( count ) + self.frames.count:SetText(count and tostring(count) or "") +end + + + + + +---------------------- +-- Event Handlers +---------------------- +function RAAD:PostClick() + self:UpdateInUse() +end + +function RAAD:OnDragStart() + if LOCK_ACTIONBAR ~= "1" or IsShiftKeyDown() then + self:PickupAction() + end +end + +function RAAD:OnReceiveDrag() + self:PlaceAction() +end + +function RAAD:OnEnter() + self:SetTooltip() -- from ReAction base class + self.tooltipTime = TOOLTIP_UPDATE_TIME +end + +function RAAD:OnLeave() + self:ClearTooltip() -- from ReAction base class + self.tooltipTime = nil +end + +function RAAD:OnUpdate(elapsed) + -- handle flashing + if self:IsFlashing() then + self.flashtime = self.flashtime - elapsed + if self.flashtime <= 0 then + local overtime = -self.flashtime + if overtime >= ATTACK_BUTTON_FLASH_TIME then + overtime = 0 + end + self.flashtime = ATTACK_BUTTON_FLASH_TIME - overtime + + local f = self.frames.flash + if f then + if f:IsVisible() then + f:Hide() + else + f:Show() + end + end + end + end + + -- Handle range indicator + if self.rangeTimer then + self.rangeTimer = self.rangeTimer - elapsed + if self.rangeTimer <= 0 then + self:UpdateUsable() + self.rangeTimer = TOOLTIP_UPDATE_TIME + end + end + + -- handle tooltip update + if self.tooltipTime then + self.tooltipTime = self.tooltipTime - elapsed + if self.tooltipTime <= 0 then + if GameTooltip:IsOwned(self.frames.button) then + self:UpdateTooltip() + self.tooltipTime = TOOLTIP_UPDATE_TIME + else + self.tooltipTime = nil + end + end + end +end + + + +---------------------- +-- Internal methods +---------------------- + +local function placeLabel( label, anchor ) + local top = string.match(anchor,"TOP") + local bottom = string.match(anchor, "BOTTOM") + label:ClearAllPoints() + label:SetWidth(40) + label:SetPoint(top or bottom or "CENTER",0,top and 2 or bottom and -2 or 0) + local j + if string.match(anchor,"LEFT") then + j = "LEFT" + elseif string.match(anchor,"RIGHT") then + j = "RIGHT" + else + j = "CENTER" + end + label:SetJustifyH(j) +end + + +function RAAD:ApplyLayout() + local f = self.frames + + if self.config.keyBindLoc then + placeLabel(f.hotkey, self.config.keyBindLoc) + end + + if self.config.stackCountLoc then + placeLabel(f.count, self.config.stackCountLoc) + end + + if self.config.showKeyBind then + f.hotkey:Show() + else + f.hotkey:Hide() + end + + if self.config.showStackCount then + f.count:Show() + else + f.count:Hide() + end + + if self.config.showMacroName then + f.macro:Show() + else + f.macro:Hide() + end + +end + +function RAAD:ApplyStyle() + local f = self.frames + -- for now, just a static style + f.hotkey:SetFontObject(NumberFontNormal) + f.count:SetFontObject(NumberFontNormalYellow) + f.border:SetVertexColor( tcolor(equippedActionBorderColor) ) +end + +function RAAD:StartFlash() + self.flashing = true + self.flashtime = 0 +end + +function RAAD:StopFlash() + self.flashing = false + self.frames.flash:Hide() +end + +function RAAD:IsFlashing() + return self.flashing +end + +function RAAD:DisplayVisibility() + local b = self.frames.button + + if b:GetAttribute("statehidden") then + -- can't hide/show in combat + if not InCombatLockdown() then + b:Hide() + end + elseif not self:IsActionEmpty() then + b:GetNormalTexture():SetAlpha(1.0) + b:SetAlpha(1) + elseif self.showTmp_ and self.showTmp_ > 0 or self.config.showGrid then + b:GetNormalTexture():SetAlpha(0.5) + self.frames.cooldown:Hide() + b:SetAlpha(1) + else + b:SetAlpha(0) + end +end +