Repository navigation
Expand file tree
/
Copy pathPicker.lua
More file actions
295 lines (266 loc) · 9.83 KB
/
Copy pathPicker.lua
File metadata and controls
295 lines (266 loc) · 9.83 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
---------------------------------------------------------
-- CastCount - Button picker
-- Author: Dranged
---------------------------------------------------------
-- The keybind-style selection mode: every action button on screen gets a
-- clickable cover. A click toggles the button; with Shift, its whole bar.
local ADDON, CC = ...
local UI = CC.UI
local overlays = {} -- button -> cover
local active = false
local function IsSelected(btn) return CC.char.buttons[btn:GetName()] and true or false end
local function SetSelected(btn, on)
CC.char.buttons[btn:GetName()] = on or nil
end
function CC.SelectedCount()
local n = 0
for _ in pairs(CC.char.buttons) do n = n + 1 end
return n
end
local function Paint(o)
local sel = IsSelected(o.btn)
if sel then
o.fill:SetColorTexture(0.1, 0.8, 0.25, 0.35)
o:SetBackdropBorderColor(0.2, 1, 0.35, 1)
else
o.fill:SetColorTexture(0, 0, 0, 0.55)
o:SetBackdropBorderColor(0.45, 0.45, 0.45, 0.9)
end
o.check:SetShown(sel)
end
-- Hover highlight: white-blue = clicking adds, red = clicking removes.
local ADD_COLOR = { 0.7, 0.9, 1 }
local REMOVE_COLOR = { 1, 0.2, 0.2 }
local hovered -- the cover under the mouse
-- The covers a click on o would change: o alone, or with Shift its whole bar (on screen).
local function Group(o)
if not IsShiftKeyDown() then return { o } end
local key, group = CC.BarKey(o.btn), {}
for _, other in pairs(overlays) do
if other:IsShown() and CC.BarKey(other.btn) == key then group[#group + 1] = other end
end
return group
end
-- A click removes when everything it would change is already selected, otherwise it adds.
local function ClickRemoves(group)
for _, o in ipairs(group) do
if not IsSelected(o.btn) then return false end
end
return true
end
local function PaintHover()
for _, o in pairs(overlays) do o.hover:Hide() end
if not (active and hovered and hovered:IsShown()) then return end
local group = Group(hovered)
local c = ClickRemoves(group) and REMOVE_COLOR or ADD_COLOR
for _, o in ipairs(group) do
o.hover:SetColorTexture(c[1], c[2], c[3], 0.4)
o.hover:Show()
end
end
function CC.RepaintPicker()
for _, o in pairs(overlays) do
if o:IsShown() then Paint(o) end
end
PaintHover()
end
local function ShowTooltip(o)
GameTooltip:SetOwner(o, "ANCHOR_TOP")
local spell = CC.ButtonSpell(o.btn)
local name = spell and CC.SpellName(spell)
GameTooltip:AddLine(name or "Empty button", 1, 1, 1)
GameTooltip:AddLine(IsSelected(o.btn) and "|cff33ff55Shows a cast count|r" or "|cff999999No cast count|r")
local removes = ClickRemoves(Group(o))
if IsShiftKeyDown() then
GameTooltip:AddLine(removes and "Click: remove this bar" or "Click: add this bar", 0.8, 0.8, 0.8)
else
GameTooltip:AddLine(removes and "Click: remove this button" or "Click: add this button", 0.8, 0.8, 0.8)
GameTooltip:AddLine("Hold Shift for the whole bar", 0.6, 0.6, 0.6)
end
GameTooltip:Show()
end
-- Click toggles: if everything it covers is selected it's removed, otherwise it's added.
-- With Shift it acts on the whole bar, including empty buttons that aren't on screen.
local function OnClick(o)
if InCombatLockdown() then return end
local add = not ClickRemoves(Group(o))
if IsShiftKeyDown() then
local key = CC.BarKey(o.btn)
for _, btn in ipairs(CC.Candidates(false)) do
if CC.BarKey(btn) == key then SetSelected(btn, add) end
end
else
SetSelected(o.btn, add)
end
CC.RepaintPicker()
CC.MarkDirty()
UI.RefreshAll()
if GameTooltip:GetOwner() == o then ShowTooltip(o) end
end
local function Overlay(btn)
local o = overlays[btn]
if o then return o end
o = CreateFrame("Button", nil, UIParent, "BackdropTemplate")
o:SetFrameStrata("DIALOG")
o:SetAllPoints(btn)
o:SetBackdrop({ edgeFile = UI.WHITE, edgeSize = 2 })
o.fill = o:CreateTexture(nil, "BACKGROUND")
o.fill:SetPoint("TOPLEFT", 2, -2)
o.fill:SetPoint("BOTTOMRIGHT", -2, 2)
o.hover = o:CreateTexture(nil, "ARTWORK")
o.hover:SetAllPoints(o.fill)
o.hover:Hide()
o.check = o:CreateTexture(nil, "OVERLAY")
o.check:SetTexture("Interface\\Buttons\\UI-CheckBox-Check")
o.check:SetSize(18, 18)
o.check:SetPoint("TOPRIGHT", 3, 3)
o:RegisterForClicks("LeftButtonUp")
o:SetScript("OnClick", OnClick)
o:SetScript("OnEnter", function(self)
hovered = self
PaintHover()
ShowTooltip(self)
end)
o:SetScript("OnLeave", function(self)
if hovered == self then hovered = nil end
PaintHover()
GameTooltip:Hide()
end)
o.btn = btn
overlays[btn] = o
return o
end
-- Pressing or releasing Shift while hovering switches between button and bar.
CC.On("MODIFIER_STATE_CHANGED", function()
if not (active and hovered) then return end
PaintHover()
if GameTooltip:GetOwner() == hovered then ShowTooltip(hovered) end
end)
-- Covers every button on screen. Returns false (with a message) in combat.
function CC.StartPicking()
if InCombatLockdown() then
CC.Print("Button selection opens after combat.")
return false
end
active = true
for _, o in pairs(overlays) do o:Hide() end
for _, btn in ipairs(CC.Candidates(true)) do Overlay(btn):Show() end
CC.RepaintPicker()
return true
end
function CC.StopPicking()
active = false
hovered = nil
for _, o in pairs(overlays) do
if GameTooltip:GetOwner() == o then GameTooltip:Hide() end
o:Hide()
end
end
function CC.IsPicking() return active end
---------------------------------------------------------
-- SECTION: Button Mode
---------------------------------------------------------
-- Like the game's Quick Keybind Mode (/kb): the settings close, your bars are
-- covered, and a popup sums up the controls. Okay keeps the changes; Cancel (or
-- Escape) puts the selection back the way it was. Either way the settings reopen.
local modeActive, before, dialog
local function Dialog()
if dialog then return dialog end
dialog = CreateFrame("Frame", "CastCountButtonMode", UIParent, "BackdropTemplate")
dialog:SetSize(540, 244)
dialog:SetPoint("TOP", UIParent, "TOP", 0, -120)
dialog:SetFrameStrata("FULLSCREEN_DIALOG")
UI.Backdrop(dialog, 0.05, 0.05, 0.06, 0.95, 0.4, 0.4, 0.42, 1)
dialog:EnableMouse(true)
dialog:SetMovable(true)
dialog:SetClampedToScreen(true)
dialog:RegisterForDrag("LeftButton")
dialog:SetScript("OnDragStart", dialog.StartMoving)
dialog:SetScript("OnDragStop", dialog.StopMovingOrSizing)
local title = UI.Text(dialog, "CastCount Button Mode", "GameFontNormalLarge")
title:SetPoint("TOP", 0, -14)
title:SetJustifyH("CENTER")
local body = UI.Text(dialog, "You are in CastCount Button Mode. Perform the below actions on your action buttons.\n\n"
.. "|cffffd100Click|r to add/remove CastCount on the action button\n"
.. "|cffffd100Shift+Click|r to add/remove CastCount on the whole action bar\n\n"
.. "Already selected buttons are |cff33ff55green|r.")
body:SetPoint("TOP", 0, -44)
body:SetWidth(490)
body:SetJustifyH("CENTER")
local cancelNote = UI.Text(dialog, "Add All adds every action button on screen. "
.. "Canceling will undo your changes and leave CastCount Button Mode.")
cancelNote:SetPoint("BOTTOM", 0, 50)
cancelNote:SetWidth(490)
cancelNote:SetJustifyH("CENTER")
-- Okay | Add All | Remove All | Cancel, evenly spaced along the bottom.
local buttons = {
{ OKAY or "Okay", function() CC.EndButtonMode(true, true) end },
{ "Add All", function() CC.SelectAllVisible() end },
{ "Remove All", function() CC.ClearSelection() end },
{ CANCEL or "Cancel", function() CC.EndButtonMode(false, true) end },
}
local bw, gap = 115, 13
local x = (540 - (#buttons * bw + (#buttons - 1) * gap)) / 2
for _, def in ipairs(buttons) do
local b = UI.Button(dialog, def[1], bw, 24, def[2])
b:SetPoint("BOTTOMLEFT", x, 16)
x = x + bw + gap
end
-- Escape hides the popup: that counts as Cancel.
dialog:SetScript("OnHide", function()
if modeActive then CC.EndButtonMode(false, true) end
end)
tinsert(UISpecialFrames, "CastCountButtonMode")
return dialog
end
function CC.StartButtonMode()
if modeActive then return end
if InCombatLockdown() then
CC.Print("Button Mode opens after combat.")
return
end
modeActive = true
before = CC.CopyDeep(CC.char.buttons)
if CC.HideConfig then CC.HideConfig() end
CC.StartPicking()
Dialog():Show()
end
-- keep: keep the changes (Okay) or put the old selection back (Cancel);
-- reopen: show the settings again afterwards.
function CC.EndButtonMode(keep, reopen)
if not modeActive then return end
modeActive = false
if not keep and before then
wipe(CC.char.buttons)
for name, on in pairs(before) do CC.char.buttons[name] = on end
end
before = nil
CC.StopPicking()
if dialog then dialog:Hide() end
CC.MarkDirty()
UI.RefreshAll()
if reopen and CC.ShowConfig then CC.ShowConfig() end
end
function CC.InButtonMode() return modeActive end
-- The covers would swallow clicks meant for spells, so combat always ends the mode.
CC.On("PLAYER_REGEN_DISABLED", function()
if modeActive then
CC.EndButtonMode(true, false)
CC.Print("Button Mode closed for combat; your changes are kept.")
elseif active then
CC.StopPicking()
end
end)
-- Adds every button on screen.
function CC.SelectAllVisible()
for _, btn in ipairs(CC.Candidates(true)) do SetSelected(btn, true) end
CC.RepaintPicker()
CC.MarkDirty()
UI.RefreshAll()
end
function CC.ClearSelection()
wipe(CC.char.buttons)
CC.RepaintPicker()
CC.MarkDirty()
UI.RefreshAll()
end