vanilla-wow-addons – Blame information for rev 1

Subversion Repositories:
Rev:
Rev Author Line No. Line
1 office 1  
2 --[[ TrinketMenu 2.6 ]]--
3  
4 --[[ SavedVariables ]]--
5  
6 -- global settings
7 TrinketMenuOptions = {
8 IconPos = -100, -- angle of initial minimap icon position
9 CooldownCount = "OFF", -- whether to display numerical cooldown counters
10 TooltipFollow = "OFF", -- whether tooltips follow the mouse
11 KeepOpen = "OFF", -- whether menu hides after use
12 ShowIcon = "ON", -- whether to show the minimap button
13 KeepDocked = "ON", -- whether to keep menu docked at all times
14 Notify = "OFF", -- whether a message appears when a trinket is ready
15 DisableToggle="OFF", -- whether minimap button toggles trinkets
16 NotifyUsedOnly="OFF", -- whether notify happens only on trinkets used
17 NotifyChatAlso="OFF", -- whether to send notify to chat also
18 Locked = "OFF", -- whether windows can be moved/scaled/rotated
19 ShowTooltips = "ON", -- whether to display tooltips at all
20 NotifyThirty = "OFF", -- whether to notify cooldowns at 30 seconds instead of 0
21 SquareMinimap = "OFF", -- whether the minimap is square instead of circular
22 MenuOnShift = "OFF" -- whether menu requires Shift to display
23 }
24  
25 -- per-character settings
26 TrinketMenuPerOptions = {
27 MainDock = "BOTTOMRIGHT", -- corner of main window docked to
28 MenuDock = "BOTTOMLEFT", -- corner menu window is docked from
29 MainOrient = "HORIZONTAL", -- direction of main window
30 MenuOrient = "VERTICAL", -- direction of menu window
31 XPos = 400, -- left edge of main window
32 YPos = 400, -- top edge of main window
33 MainScale = 1, -- scaling of main window
34 MenuScale = 1, -- scaling of menu window
35 Visible="ON", -- whether to display the trinkets
36 FirstUse = true -- whether this is the first time this user has used the mod
37 }
38  
39 --[[ Misc Variables ]]--
40  
41 TrinketMenu_Version = 2.7
42 BINDING_HEADER_TRINKETMENU = "TrinketMenu"
43  
44 TrinketMenu = {}
45  
46 TrinketMenu.MaxTrinkets = 30 -- add more to TrinketMenu_MenuFrame if this changes
47  
48 TrinketMenu.BaggedTrinkets = {} -- indexed by number, 1-30 of trinkets in the menu
49 TrinketMenu.NumberOfTrinkets = 0 -- number of trinkets in the menu
50 TrinketMenu.Swapping = false -- true if a swap in progress
51  
52 TrinketMenu.ScalingTime = 0 -- time since last scaling OnUpdate
53 TrinketMenu.ScalingUpdateTimer = .1 -- frequency (in seconds) of scaling OnUpdates
54 TrinketMenu.FrameToScale = nil -- handle to the frame (_MainFrame or _MenuFrame) being scaled
55 TrinketMenu.ScalingWidth = 0 -- width of the frame being scaled
56  
57 TrinketMenu.DockingTime = 0 -- time since last docking OnUpdate
58 TrinketMenu.DockingUpdateTimer = .2 -- frequency (in seconds) of docking OnUpdates
59  
60 TrinketMenu.InventoryTime = 0 -- time since last inventory/bag change
61 TrinketMenu.InventoryUpdateTimer = .25 -- time after last inventory/bag change before doing an update
62  
63 TrinketMenu.MenuFrameTime = 0 -- time since last MenuFrame OnUpdate
64 TrinketMenu.MenuFrameUpdateTimer = .25 -- time before menu disappears after leaving main/menu frames
65  
66 TrinketMenu.TooltipTime = 0 -- time since last tooltip OnUpdate
67 TrinketMenu.TooltipUpdateTimer = 1 -- frequency (in seconds) of updating tooltip
68 TrinketMenu.TooltipOwner = nil -- (this) when tooltip created
69 TrinketMenu.TooltipType = nil -- "BAG" or "INVENTORY"
70 TrinketMenu.TooltipBag = nil -- bag number
71 TrinketMenu.TooltipSlot = nil -- bag or inventory slot number
72  
73 TrinketMenu.CooldownCountTime = 0 -- time since last cooldown numbers update
74 TrinketMenu.CooldownCountUpdateTimer = 1 -- frequency (in seconds) of updating cooldown numbers
75 TrinketMenu.CurrentTime = 0 -- time when a cooldown pass begins
76  
77 TrinketMenu.Queue = {} -- [0] or [1] = name of trinket queued for slot 0 or 1
78 TrinketMenu.NotifyList = {} -- name of trinkets used to be notified when cooldown expires
79  
80 -- option labels, tooltips and variables
81 TrinketMenu.OptInfo = {
82 ["TrinketMenuOptShowIcon"] = { text="Minimap Button", tooltip="Check this to show a gear button along the minimap edge to access TrinketMenu.\n\n/trinket opt : display options", info="ShowIcon" },
83 ["TrinketMenuOptLocked"] = { text="Lock Windows", tooltip="Check this to lock the windows to prevent moving, scaling or rotating.", info="Locked" },
84 ["TrinketMenuOptCooldownCount"] = { text="Cooldown Numbers", tooltip="Check this to show numerical cooldowns remaining on trinkets.", info="CooldownCount" },
85 ["TrinketMenuOptShowTooltips"] = { text="Show Tooltips", tooltip="Check this to show tooltips for trinkets and options.", info="ShowTooltips" },
86 ["TrinketMenuOptTooltipFollow"] = { text="Tooltips at Mouse", tooltip="Check this to show trinket tooltips at the pointer instead of the default position.", info="TooltipFollow" },
87 ["TrinketMenuOptKeepOpen"] = { text="Keep Menu Open", tooltip="Check this to keep the trinket menu open at all times.", info="KeepOpen" },
88 ["TrinketMenuOptKeepDocked"] = { text="Keep Menu Docked", tooltip="Check this to keep the trinket menu docked to the equipped trinkets.\n\nRecommended: On\n\nIf you undock and move the menu far away from equipped trinkets, you may not be able to move the mouse to the menu before it disappears. If this happens, hold Shift to keep the menu open or check this option to redock the window.", info="KeepDocked" },
89 ["TrinketMenuOptNotify"] = { text="Notify When Ready", tooltip="Check this to display a message when a trinket's cooldown is expiring.", info="Notify" },
90 ["TrinketMenuOptDisableToggle"] = { text="Disable Toggle", tooltip="Check this to prevent clicking the minimap button from toggling the trinkets on/off.", info="DisableToggle" },
91 ["TrinketMenuOptNotifyUsedOnly"] = { text="Notify Used Only", tooltip="Check this to show cooldown notifications only if you actually used the trinket. So that equip cooldowns and shared timers will not notify on expiring.", info="NotifyUsedOnly" },
92 ["TrinketMenuOptNotifyChatAlso"] = { text="Notify Chat Also", tooltip="Check this to send cooldown notifications to the chat window also.", info="NotifyChatAlso" },
93 ["TrinketMenuOptNotifyThirty"] = { text="Notify at 30 sec", tooltip="Check this to send cooldown notifications when a trinket is at 30 seconds.", info="NotifyThirty" },
94 ["TrinketMenuOptSquareMinimap"] = { text="Square Minimap", tooltip="Check this to position the minimap button on a square minimap.", info="SquareMinimap" },
95 ["TrinketMenuOptMenuOnShift"] = { text="Menu On Shift Only", tooltip="Check this to prevent the trinket menu from showing unless you hold Shift.", info="MenuOnShift" }
96 }
97  
98 --[[ Local functions ]]--
99  
100 -- dock-dependant offset and directions: MainDock..MenuDock
101 -- x/yoff = offset MenuFrame is positioned to MainFrame
102 -- x/ydir = direction trinkets are added to menu
103 -- x/ystart = starting offset when building a menu, relativePoint MenuDock
104 local dock_stats = { ["TOPRIGHTTOPLEFT"] = { xoff=-4, yoff=0, xdir=1, ydir=-1, xstart=8, ystart=-8 },
105 ["BOTTOMRIGHTBOTTOMLEFT"] = { xoff=-4, yoff=0, xdir=1, ydir=1, xstart=8, ystart=44 },
106 ["TOPLEFTTOPRIGHT"] = { xoff=4, yoff=0, xdir=-1, ydir=-1, xstart=-44, ystart=-8 },
107 ["BOTTOMLEFTBOTTOMRIGHT"] = { xoff=4, yoff=0, xdir=-1, ydir=1, xstart=-44, ystart=44 },
108 ["TOPRIGHTBOTTOMRIGHT"] = { xoff=0, yoff=-4, xdir=-1, ydir=1, xstart=-44, ystart=44 },
109 ["BOTTOMRIGHTTOPRIGHT"] = { xoff=0, yoff=4, xdir=-1, ydir=-1, xstart=-44, ystart=-8 },
110 ["TOPLEFTBOTTOMLEFT"] = { xoff=0, yoff=-4, xdir=1, ydir=1, xstart=8, ystart=44 },
111 ["BOTTOMLEFTTOPLEFT"] = { xoff=0, yoff=4, xdir=1, ydir=-1, xstart=8, ystart=-8 } }
112  
113 -- returns offset and direction depending on current docking. ie: dock_info("xoff")
114 local function dock_info(arg1)
115  
116 local anchor = TrinketMenuPerOptions.MainDock..TrinketMenuPerOptions.MenuDock
117  
118 if dock_stats[anchor] and arg1 and dock_stats[anchor][arg1] then
119 return dock_stats[anchor][arg1]
120 else
121 return 0
122 end
123 end
124  
125 -- hide the docking markers
126 local function clear_docking()
127  
128 local corners,i = { "TOPLEFT", "TOPRIGHT", "BOTTOMLEFT", "BOTTOMRIGHT" }
129  
130 for i=1,4 do
131 getglobal("TrinketMenu_MainDock_"..corners[i]):Hide()
132 getglobal("TrinketMenu_MenuDock_"..corners[i]):Hide()
133 end
134 end
135  
136 -- returns true if the two values are close to each other
137 local function near(arg1,arg2)
138  
139 local isnear = false
140  
141 if (math.max(arg1,arg2)-math.min(arg1,arg2)) < 15 then
142 isnear = true
143 end
144  
145 return isnear
146 end
147  
148 -- returns true if windows unlocked
149 local function unlocked()
150 return TrinketMenuOptions.Locked=="OFF"
151 end
152  
153 -- moves the MenuFrame to the dock position against MainFrame
154 local function dock_windows()
155  
156 clear_docking()
157  
158 if TrinketMenuOptions.KeepDocked=="ON" then
159  
160 TrinketMenu_MenuFrame:ClearAllPoints()
161 if TrinketMenuOptions.Locked=="OFF" then
162 TrinketMenu_MenuFrame:SetPoint(TrinketMenuPerOptions.MenuDock,"TrinketMenu_MainFrame",TrinketMenuPerOptions.MainDock,dock_info("xoff"),dock_info("yoff"))
163 else
164 TrinketMenu_MenuFrame:SetPoint(TrinketMenuPerOptions.MenuDock,"TrinketMenu_MainFrame",TrinketMenuPerOptions.MainDock,dock_info("xoff")*3,dock_info("yoff")*3)
165 end
166 end
167 end
168  
169 -- displays windows vertically or horizontally
170 local function orient_windows()
171  
172 if TrinketMenuPerOptions.MainOrient=="HORIZONTAL" then
173 TrinketMenu_MainFrame:SetWidth(90)
174 TrinketMenu_MainFrame:SetHeight(52)
175 else
176 TrinketMenu_MainFrame:SetWidth(52)
177 TrinketMenu_MainFrame:SetHeight(90)
178 end
179  
180 TrinketMenu.InventoryTime = 10 -- immediate update
181 TrinketMenu_InventoryFrame:Show()
182  
183 end
184  
185 -- redisplay menu cooldowns only if they're on screen
186 local function update_menu_cooldowns()
187  
188 -- set cooldown timers on menu trinkets
189 local start, duration, enable
190 for i=1,TrinketMenu.NumberOfTrinkets do
191 start,duration,enable = GetContainerItemCooldown(TrinketMenu.BaggedTrinkets[i].bag,TrinketMenu.BaggedTrinkets[i].slot)
192 CooldownFrame_SetTimer(getglobal("TrinketMenu_Menu"..i.."Cooldown"), start, duration, enable)
193 end
194 end
195  
196 -- update equipped trinkets cooldowns
197 local function update_cooldowns()
198  
199 local start, duration, enable
200  
201 start, duration, enable = GetInventoryItemCooldown("player",13)
202 CooldownFrame_SetTimer(TrinketMenu_Trinket0Cooldown, start, duration, enable)
203  
204 start, duration, enable = GetInventoryItemCooldown("player",14)
205 CooldownFrame_SetTimer(TrinketMenu_Trinket1Cooldown, start, duration, enable)
206  
207 if TrinketMenu_MenuFrame:IsVisible() and TrinketMenu.NumberOfTrinkets>0 then
208 update_menu_cooldowns()
209 end
210 end
211  
212 -- call this when any action can change the 'Cooldown Numbers' or 'Notify When Ready' options
213 -- both share the same OnUpdate frame, but either should work independently of other.
214 local function cooldown_opts_changed()
215  
216 local i
217  
218 if TrinketMenuOptions.CooldownCount=="OFF" then
219 TrinketMenu_Trinket0Time:Hide("")
220 TrinketMenu_Trinket1Time:Hide("")
221 for i=1,TrinketMenu.MaxTrinkets do
222 getglobal("TrinketMenu_Menu"..i.."Time"):Hide("")
223 end
224 else
225 TrinketMenu_Trinket0Time:Show()
226 TrinketMenu_Trinket1Time:Show()
227 for i=1,TrinketMenu.MaxTrinkets do
228 getglobal("TrinketMenu_Menu"..i.."Time"):Show()
229 end
230 end
231 end
232  
233  
234 -- scan inventory and build MenuFrame
235 function TrinketMenu_BuildMenu()
236  
237 local idx,i,j,k,texture = 1
238 local itemLink,itemID,itemName,equipSlot,itemTexture
239  
240 -- go through bags and gather trinkets into .BaggedTrinkets
241 for i=0,4 do
242 for j=1,GetContainerNumSlots(i) do
243 itemLink = GetContainerItemLink(i,j)
244  
245 if itemLink then
246 _,_,itemID,itemName = string.find(GetContainerItemLink(i,j) or "","item:(%d+).+%[(.+)%]")
247 _,_,_,_,_,_,_,equipSlot,itemTexture = GetItemInfo(itemID or "")
248 if equipSlot=="INVTYPE_TRINKET" then
249 if not TrinketMenu.BaggedTrinkets[idx] then
250 TrinketMenu.BaggedTrinkets[idx] = {}
251 end
252 TrinketMenu.BaggedTrinkets[idx].bag = i
253 TrinketMenu.BaggedTrinkets[idx].slot = j
254 TrinketMenu.BaggedTrinkets[idx].name = itemName
255 TrinketMenu.BaggedTrinkets[idx].texture = itemTexture
256 idx = idx + 1
257 end
258 end
259 end
260 end
261 TrinketMenu.NumberOfTrinkets = math.min(idx-1,TrinketMenu.MaxTrinkets)
262  
263 if TrinketMenu.NumberOfTrinkets<1 then
264 -- user has no bagged trinkets :(
265 TrinketMenu_MenuFrame:Hide()
266 else
267 -- display trinkets outward from docking point
268 local col,row,xpos,ypos = 0,0,dock_info("xstart"),dock_info("ystart")
269 local max_cols = 1
270  
271 if TrinketMenu.NumberOfTrinkets>24 then
272 max_cols = 5
273 elseif TrinketMenu.NumberOfTrinkets>18 then
274 max_cols = 4
275 elseif TrinketMenu.NumberOfTrinkets>12 then
276 max_cols = 3
277 elseif TrinketMenu.NumberOfTrinkets>4 then
278 max_cols = 2
279 end
280  
281 for i=1,TrinketMenu.NumberOfTrinkets do
282 local item = getglobal("TrinketMenu_Menu"..i)
283 getglobal("TrinketMenu_Menu"..i.."Icon"):SetTexture(TrinketMenu.BaggedTrinkets[i].texture)
284 item:SetPoint("TOPLEFT","TrinketMenu_MenuFrame",TrinketMenuPerOptions.MenuDock,xpos,ypos)
285  
286 if TrinketMenuPerOptions.MenuOrient=="VERTICAL" then
287 xpos = xpos + dock_info("xdir")*40
288 col = col + 1
289 if col==max_cols then
290 xpos = dock_info("xstart")
291 col = 0
292 ypos = ypos + dock_info("ydir")*40
293 row = row + 1
294 end
295 item:Show()
296 else
297 ypos = ypos + dock_info("ydir")*40
298 col = col + 1
299 if col==max_cols then
300 ypos = dock_info("ystart")
301 col = 0
302 xpos = xpos + dock_info("xdir")*40
303 row = row + 1
304 end
305 item:Show()
306 end
307 end
308 for i=(TrinketMenu.NumberOfTrinkets+1),TrinketMenu.MaxTrinkets do
309 getglobal("TrinketMenu_Menu"..i):Hide()
310 end
311 if col==0 then
312 row = row-1
313 end
314  
315 if TrinketMenuPerOptions.MenuOrient=="VERTICAL" then
316 TrinketMenu_MenuFrame:SetWidth(12+(max_cols*40))
317 TrinketMenu_MenuFrame:SetHeight(12+((row+1)*40))
318 else
319 TrinketMenu_MenuFrame:SetWidth(12+((row+1)*40))
320 TrinketMenu_MenuFrame:SetHeight(12+(max_cols*40))
321 end
322  
323 update_menu_cooldowns()
324 end
325  
326 end
327  
328 -- sets window lock "ON" or "OFF"
329 local function set_lock(arg1)
330  
331 TrinketMenuOptions.Locked = arg1
332  
333 if arg1=="ON" then
334 TrinketMenu_MainFrame:SetBackdropColor(0,0,0,0)
335 TrinketMenu_MainFrame:SetBackdropBorderColor(0,0,0,0)
336 TrinketMenu_MainResizeButton:Hide()
337 TrinketMenu_MenuFrame:SetBackdropColor(0,0,0,0)
338 TrinketMenu_MenuFrame:SetBackdropBorderColor(0,0,0,0)
339 TrinketMenu_MenuResizeButton:Hide()
340 else
341 TrinketMenu_MainFrame:SetBackdropColor(1,1,1,1)
342 TrinketMenu_MainFrame:SetBackdropBorderColor(1,1,1,1)
343 TrinketMenu_MainResizeButton:Show()
344 TrinketMenu_MenuFrame:SetBackdropColor(1,1,1,1)
345 TrinketMenu_MenuFrame:SetBackdropBorderColor(1,1,1,1)
346 TrinketMenu_MenuResizeButton:Show()
347 end
348 dock_windows()
349 end
350  
351 local function move_icon()
352  
353 local xpos,ypos
354  
355 if TrinketMenuOptions.SquareMinimap=="ON" then
356 -- brute force method until trig solution figured out - min/max a point on a circle beyond square
357 xpos = 110 * cos(TrinketMenuOptions.IconPos or 0)
358 ypos = 110 * sin(TrinketMenuOptions.IconPos or 0)
359 xpos = math.max(-82,math.min(xpos,84))
360 ypos = math.max(-86,math.min(ypos,82))
361 else
362 xpos = 80*cos(TrinketMenuOptions.IconPos or 0)
363 ypos = 80*sin(TrinketMenuOptions.IconPos or 0)
364 end
365  
366 TrinketMenu_IconFrame:SetPoint("TOPLEFT","Minimap","TOPLEFT",52-xpos,ypos-52)
367  
368 end
369  
370 local function show_icon()
371 if TrinketMenuOptions.ShowIcon=="ON" then
372 TrinketMenu_IconFrame:Show()
373 else
374 TrinketMenu_IconFrame:Hide()
375 end
376 end
377  
378 local function check_state(arg1)
379  
380 if arg1=="ON" then
381 return 1
382 else
383 return 0
384 end
385 end
386  
387 -- for use with main/menu frames with UIParent parent when relocated by the mod, to register for layout-cache.txt
388 local function really_setpoint(frame,point,relativeTo,relativePoint,xoff,yoff)
389 frame:SetPoint(point,relativeTo,relativePoint,xoff,yoff)
390 end
391  
392 -- enable/disable subopt (arg2) arg1->arg2
393 local function subopt_enable(arg1,arg2)
394  
395 if arg1 and arg2 and TrinketMenuOptions[arg1]=="ON" then
396 getglobal("TrinketMenuOpt"..arg2):Enable()
397 getglobal("TrinketMenuOpt"..arg2.."Text"):SetTextColor(1,.82,0)
398 elseif arg1 and arg2 then
399 getglobal("TrinketMenuOpt"..arg2):Disable()
400 getglobal("TrinketMenuOpt"..arg2.."Text"):SetTextColor(.6,.6,.6)
401 end
402 end
403  
404 -- returns the name of the trinket in slot 0 or 1
405 local function trinket_name(slot)
406 local _,_,name = string.find(GetInventoryItemLink("player",tonumber(slot)+13) or "","^.*%[(.*)%].*$")
407 return name
408 end
409  
410 -- sets initial display
411 local function initialize_display()
412  
413 if TrinketMenuPerOptions.FirstUse then
414 -- if this is first use for this user
415 local i
416 for i in TrinketMenuPerOptions do
417 -- go through and see if any PerOptions are in Options from previous versions
418 if TrinketMenuOptions[i] then
419 -- copy those Options to PerOptions
420 TrinketMenuPerOptions[i] = TrinketMenuOptions[i]
421 end
422 end
423 TrinketMenuPerOptions.FirstUse = nil
424 end
425  
426 TrinketMenuOptions.KeepDocked = TrinketMenuOptions.KeepDocked or "ON" -- new option for 2.1
427 TrinketMenuOptions.Notify = TrinketMenuOptions.Notify or "OFF" -- 2.1
428 TrinketMenuOptions.DisableToggle = TrinketMenuOptions.DisableToggle or "OFF" -- new option for 2.2
429 TrinketMenuOptions.NotifyUsedOnly = TrinketMenuOptions.NotifyUsedOnly or "OFF" -- 2.2
430 TrinketMenuOptions.NotifyChatAlso = TrinketMenuOptions.NotifyChatAlso or "OFF" -- 2.2
431 TrinketMenuOptions.ShowTooltips = TrinketMenuOptions.ShowTooltips or "ON" -- 2.3
432 TrinketMenuOptions.NotifyThirty = TrinketMenuOptions.NotifyThirty or "OFF" -- 2.5
433 TrinketMenuOptions.SquareMinimap = TrinketMenuOptions.SquareMinimap or "OFF" -- 2.6
434 TrinketMenuOptions.MenuOnShift = TrinketMenuOptions.MenuOnShift or "OFF" -- 2.6
435  
436 if TrinketMenuPerOptions.XPos and TrinketMenuPerOptions.YPos then
437 really_setpoint(TrinketMenu_MainFrame,"TOPLEFT","UIParent","BOTTOMLEFT",TrinketMenuPerOptions.XPos,TrinketMenuPerOptions.YPos)
438 end
439 if TrinketMenuPerOptions.MainScale then
440 TrinketMenu_MainFrame:SetScale(TrinketMenuPerOptions.MainScale)
441 end
442 if TrinketMenuPerOptions.MenuScale then
443 TrinketMenu_MenuFrame:SetScale(TrinketMenuPerOptions.MenuScale)
444 end
445  
446 TrinketMenu_Title:SetText("TrinketMenu "..TrinketMenu_Version)
447  
448 move_icon()
449 show_icon()
450 set_lock(TrinketMenuOptions.Locked)
451 orient_windows()
452 dock_windows()
453 local _,texture = GetInventorySlotInfo("Trinket0Slot")
454 TrinketMenu_Trinket0Icon:SetTexture(texture)
455 _,texture = GetInventorySlotInfo("Trinket1Slot")
456 TrinketMenu_Trinket1Icon:SetTexture(texture)
457  
458 -- initialize options
459 for i in TrinketMenu.OptInfo do
460 getglobal(i.."Text"):SetText(TrinketMenu.OptInfo[i].text)
461 getglobal(i):SetChecked(check_state(TrinketMenuOptions[TrinketMenu.OptInfo[i].info]))
462 end
463  
464 if TrinketMenuOptions.KeepOpen=="ON" then
465 TrinketMenu_MenuFrame:Show()
466 end
467  
468 if TrinketMenuPerOptions.Visible=="OFF" then
469 TrinketMenu_MainFrame:Hide()
470 TrinketMenu_MenuFrame:Hide()
471 end
472  
473 cooldown_opts_changed()
474 subopt_enable("ShowIcon","DisableToggle")
475 subopt_enable("Notify","NotifyUsedOnly")
476 subopt_enable("Notify","NotifyChatAlso")
477 subopt_enable("Notify","NotifyThirty")
478 subopt_enable("ShowTooltips","TooltipFollow")
479 subopt_enable("ShowIcon","SquareMinimap")
480 end
481  
482 local function cursor_empty()
483 return not (CursorHasItem() or CursorHasMoney() or CursorHasSpell())
484 end
485  
486 -- swap trinket named 'name' into trinket slot 'which' (0 or 1)
487 local function swap_by_name(which,name)
488  
489 local i
490  
491 if TrinketMenu.Queue[which] and cursor_empty() then
492 for i=1,TrinketMenu.NumberOfTrinkets do
493 if TrinketMenu.BaggedTrinkets[i].name==TrinketMenu.Queue[which] then
494 PickupInventoryItem(which+13)
495 PickupContainerItem(TrinketMenu.BaggedTrinkets[i].bag,TrinketMenu.BaggedTrinkets[i].slot)
496 getglobal("TrinketMenu_Trinket"..which.."Icon"):SetVertexColor(0.4,0.4,0.4)
497 TrinketMenu.Swapping = true
498 end
499 end
500 end
501 end
502  
503 -- returns true if the player is really dead or ghost, not merely FD
504 local function player_really_dead()
505 local dead,i = UnitIsDeadOrGhost("player")
506  
507 for i=1,16 do
508 if UnitBuff("player",i)=="Interface\\Icons\\Ability_Rogue_FeignDeath" then
509 dead = nil -- player is just FD, not really dead
510 end
511 end
512  
513 return dead
514 end
515  
516 --[[ Frame Scripts ]]--
517  
518 function TrinketMenu_OnLoad()
519  
520 SlashCmdList["TrinketMenuCOMMAND"] = TrinketMenu_SlashHandler
521 SLASH_TrinketMenuCOMMAND1 = "/trinketmenu";
522 SLASH_TrinketMenuCOMMAND2 = "/trinket";
523  
524 this:RegisterEvent("PLAYER_LOGIN")
525 end
526  
527 function TrinketMenu_OnEvent(event)
528  
529 if event=="UNIT_INVENTORY_CHANGED" or event=="BAG_UPDATE" then
530 TrinketMenu.InventoryTime = 0 -- reset time of last update
531 TrinketMenu_InventoryFrame:Show()
532  
533 elseif (event=="PLAYER_REGEN_ENABLED" or event=="PLAYER_UNGHOST" or event=="PLAYER_ALIVE") and not player_really_dead() then
534 -- trinkets can now be swapped after combat/death
535 if TrinketMenu.Queue[0] or TrinketMenu.Queue[1] then
536 TrinketMenu_BuildMenu()
537 swap_by_name(0,TrinketMenu.Queue[0])
538 swap_by_name(1,TrinketMenu.Queue[1])
539 TrinketMenu.Queue[0] = nil
540 TrinketMenu.Queue[1] = nil
541 TrinketMenu_Trinket0Queue:Hide()
542 TrinketMenu_Trinket1Queue:Hide()
543 end
544  
545 elseif event=="PLAYER_ENTERING_WORLD" then
546 this:RegisterEvent("UNIT_INVENTORY_CHANGED")
547 this:RegisterEvent("BAG_UPDATE")
548 this:RegisterEvent("PLAYER_LEAVING_WORLD")
549 TrinketMenu_OnEvent("BAG_UPDATE") -- force an update
550  
551 elseif event=="PLAYER_LEAVING_WORLD" then
552 this:UnregisterEvent("UNIT_INVENTORY_CHANGED")
553 this:UnregisterEvent("BAG_UPDATE")
554 this:RegisterEvent("PLAYER_ENTERING_WORLD")
555  
556 elseif event=="PLAYER_LOGIN" then
557 table.insert(UISpecialFrames,"TrinketMenu_OptFrame") -- make options window ESCable
558  
559 initialize_display()
560  
561 -- hook UseInventoryItem
562 oldTrinketMenu_UseInventoryItem = UseInventoryItem
563 UseInventoryItem = newTrinketMenu_UseInventoryItem
564  
565 this:RegisterEvent("PLAYER_REGEN_ENABLED")
566 this:RegisterEvent("PLAYER_UNGHOST")
567 this:RegisterEvent("PLAYER_ALIVE")
568 this:RegisterEvent("PLAYER_ENTERING_WORLD")
569 end
570 end
571  
572 function TrinketMenu_SlashHandler(arg1)
573  
574 arg1 = string.lower(arg1)
575  
576 if not arg1 or arg1=="" then
577 TrinketMenu_Toggle()
578 elseif arg1=="reset" then
579 TrinketMenu_Opt_Reset()
580 elseif string.find(arg1,"^opt") or string.find(arg1,"^config") then
581 TrinketMenu_OptFrame:Show()
582 elseif arg1=="lock" then
583 set_lock("ON")
584 elseif arg1=="unlock" then
585 set_lock("OFF")
586 elseif arg1=="debug" then
587 DEFAULT_CHAT_FRAME:AddMessage("Trinkets: "..tostring(TrinketMenu.NumberOfTrinkets))
588 DEFAULT_CHAT_FRAME:AddMessage("Version: "..tostring(TrinketMenu_Version))
589 local function o(info)
590 local i=TrinketMenuOptions[info]
591 return ((i=="ON") and "1") or ((i=="OFF") and "0") or ","
592 end
593 local opts = { "CooldownCount","TooltipFollow","KeepOpen","ShowIcon","",
594 "KeepDocked","Notify", "DisableToggle", "NotifyUsedOnly","",
595 "NotifyChatAlso","Locked", "ShowTooltips", "NotifyThirty","",
596 "SquareMinimap","MenuOnShift" }
597 local txt = ""
598 for i=1,table.getn(opts) do
599 txt=txt..o(opts[i])
600 end
601 DEFAULT_CHAT_FRAME:AddMessage("Opts: "..txt)
602 elseif string.find(arg1,"scale") then
603 local _,_,menuscale = string.find(arg1,"scale menu (.+)")
604 if tonumber(menuscale) then
605 TrinketMenu.FrameToScale = TrinketMenu_MenuFrame
606 TrinketMenu_ScaleFrame(menuscale)
607 end
608 local _,_,mainscale = string.find(arg1,"scale main (.+)")
609 if tonumber(mainscale) then
610 TrinketMenu.FrameToScale = TrinketMenu_MainFrame
611 TrinketMenu_ScaleFrame(mainscale)
612 end
613 if not tonumber(menuscale) and not tonumber(mainscale) then
614 DEFAULT_CHAT_FRAME:AddMessage("|cFFFFFF00TrinketMenu scale:")
615 DEFAULT_CHAT_FRAME:AddMessage("/trinket scale main (number) : set exact main scale")
616 DEFAULT_CHAT_FRAME:AddMessage("/trinket scale menu (number) : set exact menu scale")
617 DEFAULT_CHAT_FRAME:AddMessage("ie, /trinket scale menu 0.85")
618 DEFAULT_CHAT_FRAME:AddMessage("Note: You can drag the lower-right corner of either window to scale. This slash command is for those who want to set an exact scale.")
619 end
620 TrinketMenu.FrameToScale = nil
621 TrinketMenuPerOptions.MainScale = TrinketMenu_MainFrame:GetScale()
622 TrinketMenuPerOptions.MenuScale = TrinketMenu_MenuFrame:GetScale()
623 update_cooldowns()
624 else
625 DEFAULT_CHAT_FRAME:AddMessage("|cFFFFFF00TrinketMenu useage:")
626 DEFAULT_CHAT_FRAME:AddMessage("/trinket or /trinketmenu : toggle the window")
627 DEFAULT_CHAT_FRAME:AddMessage("/trinket reset : reset window")
628 DEFAULT_CHAT_FRAME:AddMessage("/trinket opt : summon options window")
629 DEFAULT_CHAT_FRAME:AddMessage("/trinket lock|unlock : toggles window lock")
630 DEFAULT_CHAT_FRAME:AddMessage("/trinket scale main|menu (number) : sets an exact scale")
631 end
632  
633 end
634  
635 --[[ Window Movement ]]--
636  
637 function TrinketMenu_MainFrame_OnMouseUp(arg1)
638 if arg1=="LeftButton" then
639 update_cooldowns()
640 this:StopMovingOrSizing()
641 TrinketMenuPerOptions.XPos = TrinketMenu_MainFrame:GetLeft()
642 TrinketMenuPerOptions.YPos = TrinketMenu_MainFrame:GetTop()
643 elseif unlocked() then
644 if TrinketMenuPerOptions.MainOrient=="VERTICAL" then
645 TrinketMenuPerOptions.MainOrient = "HORIZONTAL"
646 else
647 TrinketMenuPerOptions.MainOrient = "VERTICAL"
648 end
649 orient_windows()
650 end
651  
652 end
653  
654 function TrinketMenu_MainFrame_OnMouseDown(arg1)
655 if arg1=="LeftButton" and unlocked() then
656 this:StartMoving()
657 end
658 end
659  
660 --[[ MainFrame and MenuFrame Scaling ]]--
661  
662 function TrinketMenu_StartScaling(arg1)
663 if arg1=="LeftButton" and unlocked() then
664 this:LockHighlight()
665 TrinketMenu.FrameToScale = this:GetParent()
666 TrinketMenu.ScalingWidth = this:GetParent():GetWidth()
667 TrinketMenu_ScalingFrame:Show()
668 end
669 end
670  
671 function TrinketMenu_StopScaling(arg1)
672 if arg1=="LeftButton" then
673 TrinketMenu_ScalingFrame:Hide()
674 TrinketMenu.FrameToScale = nil
675 this:UnlockHighlight()
676 if this:GetParent():GetName() == "TrinketMenu_MainFrame" then
677 TrinketMenuPerOptions.MainScale = TrinketMenu_MainFrame:GetScale()
678 else
679 TrinketMenuPerOptions.MenuScale = TrinketMenu_MenuFrame:GetScale()
680 end
681 update_cooldowns()
682 end
683 end
684  
685 function TrinketMenu_ScaleFrame(scale)
686 local frame = TrinketMenu.FrameToScale
687 local oldscale = frame:GetScale() or 1
688 local framex = (frame:GetLeft() or TrinketMenuPerOptions.XPos)* oldscale
689 local framey = (frame:GetTop() or TrinketMenuPerOptions.YPos)* oldscale
690  
691 frame:SetScale(scale)
692 if frame:GetName() == "TrinketMenu_MainFrame" then
693 really_setpoint(TrinketMenu_MainFrame,"TOPLEFT","UIParent","BOTTOMLEFT",framex/scale,framey/scale)
694 TrinketMenuPerOptions.XPos = TrinketMenu_MainFrame:GetLeft()
695 TrinketMenuPerOptions.YPos = TrinketMenu_MainFrame:GetTop()
696 elseif TrinketMenuOptions.KeepDocked=="OFF" then
697 TrinketMenu_MenuFrame:ClearAllPoints()
698 really_setpoint(TrinketMenu_MenuFrame,"TOPLEFT","UIParent","BOTTOMLEFT",framex/scale,framey/scale)
699 end
700 end
701  
702 function TrinketMenu_ScalingFrame_OnUpdate(arg1)
703  
704 TrinketMenu.ScalingTime = TrinketMenu.ScalingTime + arg1
705 if TrinketMenu.ScalingTime > TrinketMenu.ScalingUpdateTimer then
706 TrinketMenu.ScalingTime = 0
707  
708 local frame = TrinketMenu.FrameToScale
709 local oldscale = frame:GetEffectiveScale()
710 local framex, framey, cursorx, cursory = frame:GetLeft()*oldscale, frame:GetTop()*oldscale, GetCursorPosition()
711  
712 if (cursorx-framex)>32 then
713 local newscale = (cursorx-framex)/TrinketMenu.ScalingWidth
714 TrinketMenu_ScaleFrame(newscale)
715 end
716  
717 end
718 end
719  
720 --[[ Menu docking ]]--
721  
722 function TrinketMenu_MenuFrame_OnMouseUp(arg1)
723 if arg1=="LeftButton" then
724 update_cooldowns()
725 TrinketMenu_DockingFrame:Hide()
726 TrinketMenu_MenuFrame:StopMovingOrSizing()
727 if TrinketMenuOptions.KeepDocked=="ON" then
728 dock_windows()
729 end
730 TrinketMenu.InventoryTime = 1 -- reset time of last update
731 TrinketMenu_InventoryFrame:Show()
732 elseif unlocked() then
733 if TrinketMenuPerOptions.MenuOrient=="VERTICAL" then
734 TrinketMenuPerOptions.MenuOrient="HORIZONTAL"
735 else
736 TrinketMenuPerOptions.MenuOrient="VERTICAL"
737 end
738 orient_windows()
739 end
740 end
741  
742 function TrinketMenu_MenuFrame_OnMouseDown(arg1)
743 if arg1=="LeftButton" and unlocked() then
744 TrinketMenu_MenuFrame:StartMoving()
745  
746 if TrinketMenuOptions.KeepDocked=="ON" then
747 TrinketMenu_DockingFrame:Show()
748 end
749 end
750 end
751  
752 function TrinketMenu_DockingFrame_OnUpdate(arg1)
753  
754 TrinketMenu.DockingTime = TrinketMenu.DockingTime + arg1
755 if TrinketMenu.DockingTime > TrinketMenu.DockingUpdateTimer then
756 TrinketMenu.DockingTime = 0
757  
758 local main = TrinketMenu_MainFrame
759 local menu = TrinketMenu_MenuFrame
760 local mainscale = TrinketMenu_MainFrame:GetScale()
761 local menuscale = TrinketMenu_MenuFrame:GetScale()
762  
763 if near(main:GetRight()*mainscale,menu:GetLeft()*menuscale) then
764 if near(main:GetTop()*mainscale,menu:GetTop()*menuscale) then
765 TrinketMenuPerOptions.MainDock = "TOPRIGHT"
766 TrinketMenuPerOptions.MenuDock = "TOPLEFT"
767 elseif near(main:GetBottom()*mainscale,menu:GetBottom()*menuscale) then
768 TrinketMenuPerOptions.MainDock = "BOTTOMRIGHT"
769 TrinketMenuPerOptions.MenuDock = "BOTTOMLEFT"
770 end
771 elseif near(main:GetLeft()*mainscale,menu:GetRight()*menuscale) then
772 if near(main:GetTop()*mainscale,menu:GetTop()*menuscale) then
773 TrinketMenuPerOptions.MainDock = "TOPLEFT"
774 TrinketMenuPerOptions.MenuDock = "TOPRIGHT"
775 elseif near(main:GetBottom()*mainscale,menu:GetBottom()*menuscale) then
776 TrinketMenuPerOptions.MainDock = "BOTTOMLEFT"
777 TrinketMenuPerOptions.MenuDock = "BOTTOMRIGHT"
778 end
779 elseif near(main:GetRight()*mainscale,menu:GetRight()*menuscale) then
780 if near(main:GetTop()*mainscale,menu:GetBottom()*menuscale) then
781 TrinketMenuPerOptions.MainDock = "TOPRIGHT"
782 TrinketMenuPerOptions.MenuDock = "BOTTOMRIGHT"
783 elseif near(main:GetBottom()*mainscale,menu:GetTop()*menuscale) then
784 TrinketMenuPerOptions.MainDock = "BOTTOMRIGHT"
785 TrinketMenuPerOptions.MenuDock = "TOPRIGHT"
786 end
787 elseif near(main:GetLeft()*mainscale,menu:GetLeft()*menuscale) then
788 if near(main:GetTop()*mainscale,menu:GetBottom()*menuscale) then
789 TrinketMenuPerOptions.MainDock = "TOPLEFT"
790 TrinketMenuPerOptions.MenuDock = "BOTTOMLEFT"
791 elseif near(main:GetBottom()*mainscale,menu:GetTop()*menuscale) then
792 TrinketMenuPerOptions.MainDock = "BOTTOMLEFT"
793 TrinketMenuPerOptions.MenuDock = "TOPLEFT"
794 end
795 end
796  
797 clear_docking()
798 getglobal("TrinketMenu_MainDock_"..TrinketMenuPerOptions.MainDock):Show()
799 getglobal("TrinketMenu_MenuDock_"..TrinketMenuPerOptions.MenuDock):Show()
800  
801 end
802 end
803  
804 --[[ Inventory ]]--
805  
806 -- after a period of no inventory/bag updates since one happens, update
807 function TrinketMenu_InventoryFrame_OnUpdate(arg1)
808  
809 TrinketMenu.InventoryTime = TrinketMenu.InventoryTime + arg1
810 if TrinketMenu.InventoryTime>TrinketMenu.InventoryUpdateTimer then
811 TrinketMenu_InventoryFrame:Hide()
812 TrinketMenu.InventoryTime = 0
813  
814 local t0texture, t1texture = GetInventoryItemTexture("player",13), GetInventoryItemTexture("player",14)
815  
816 TrinketMenu.Swapping = false
817  
818 TrinketMenu_Trinket0Icon:SetTexture(t0texture or "Interface\\PaperDoll\\UI-PaperDoll-Slot-Trinket")
819 TrinketMenu_Trinket1Icon:SetTexture(t1texture or "Interface\\PaperDoll\\UI-PaperDoll-Slot-Trinket")
820 TrinketMenu_Trinket0:SetChecked(0)
821 TrinketMenu_Trinket1:SetChecked(0)
822 TrinketMenu_Trinket0Icon:SetVertexColor(1,1,1,1)
823 TrinketMenu_Trinket1Icon:SetVertexColor(1,1,1,1)
824 TrinketMenu.CooldownCountTime = TrinketMenu.CooldownCountUpdateTimer -- immediate update of cooldown counters
825 update_cooldowns()
826  
827 if not t0texture and not t1texture and TrinketMenu.NumberOfTrinkets<1 then
828 -- user has no trinkets at all. :( poor guy. hide window
829 -- TrinketMenuPerOptions.Visible = "OFF"
830 TrinketMenu_MainFrame:Hide()
831 end
832  
833 TrinketMenu_BuildMenu()
834  
835 end
836 end
837  
838 --[[ Menu popup ]]--
839  
840 function TrinketMenu_ResetMenuTimer()
841 TrinketMenu.MenuFrameTime = 0
842 end
843  
844 function TrinketMenu_MenuFrame_OnUpdate(arg1)
845  
846 TrinketMenu.MenuFrameTime = TrinketMenu.MenuFrameTime + arg1
847 if TrinketMenu.MenuFrameTime>TrinketMenu.MenuFrameUpdateTimer then
848 TrinketMenu.MenuFrameTime = 0
849 if (not MouseIsOver(TrinketMenu_MainFrame)) and (not MouseIsOver(TrinketMenu_MenuFrame)) and (not TrinketMenu_ScalingFrame:IsVisible()) and not IsShiftKeyDown() and (TrinketMenuOptions.KeepOpen=="OFF") then
850 TrinketMenu_MenuFrame:Hide()
851 end
852 end
853  
854 end
855  
856 function TrinketMenu_ShowMenu()
857  
858 if IsShiftKeyDown() or TrinketMenuOptions.MenuOnShift=="OFF" then
859 TrinketMenu_BuildMenu()
860 if TrinketMenu.NumberOfTrinkets>0 then
861 TrinketMenu.MenuFrameTime = 0
862 TrinketMenu_MenuFrame:Show()
863 end
864 end
865 end
866  
867 function TrinketMenu_Toggle()
868  
869 if TrinketMenu_MainFrame:IsVisible() then
870 TrinketMenuPerOptions.Visible = "OFF"
871 TrinketMenu_MainFrame:Hide()
872 TrinketMenu_MenuFrame:Hide()
873 TrinketMenu_OptFrame:Hide()
874 else
875 TrinketMenuPerOptions.Visible = "ON"
876 TrinketMenu_MainFrame:Show()
877 if TrinketMenuOptions.KeepOpen=="ON" then
878 TrinketMenu_MenuFrame:Show()
879 end
880 end
881 end
882  
883 --[[ Trinket clicks ]]--
884  
885 -- hooked UseInventoryItem - updates trinketmenu when slot 13 or 14 are used
886 function newTrinketMenu_UseInventoryItem(arg1)
887  
888 oldTrinketMenu_UseInventoryItem(arg1)
889  
890 if arg1==13 or arg1==14 then
891 getglobal("TrinketMenu_Trinket"..(arg1-13)):SetChecked(1)
892  
893 local name = trinket_name(arg1-13)
894 if name then
895 TrinketMenu.NotifyList[name] = 1 -- add this trinket's name to notify list
896 end
897 update_cooldowns()
898  
899 TrinketMenu.InventoryTime = -1.25
900 TrinketMenu_InventoryFrame:Show()
901 end
902 end
903  
904 -- can be used in key binding also, arg1==13 or 14
905 function TrinketMenu_UseTrinket(arg1)
906  
907 if (arg1==13 or arg1==14) and not MerchantFrame:IsVisible() then
908 UseInventoryItem(arg1)
909 end
910 end
911  
912 -- called from Trinket0/1's OnClick
913 function TrinketMenu_Trinket_OnClick(arg1)
914  
915 local id = this:GetID()
916 this:SetChecked(0)
917  
918 if arg1=="LeftButton" and IsShiftKeyDown() and ChatFrameEditBox:IsVisible() then
919 -- link to chat instead of use
920 ChatFrameEditBox:Insert(GetInventoryItemLink("player",id))
921 else
922 TrinketMenu_UseTrinket(id)
923 end
924 end
925  
926 -- called from Menu1-30's OnClick
927 function TrinketMenu_SwapTrinket(arg1)
928  
929 local id = this:GetID()
930 this:SetChecked(0)
931  
932 if UnitAffectingCombat("player") or player_really_dead() then
933 -- if in combat, put the chosen trinket(id) into queue
934  
935 local which = arg1=="LeftButton" and 0 or 1 -- which==which trinket, 0(left) or 1(right)
936  
937 if TrinketMenu.Queue[which]==TrinketMenu.BaggedTrinkets[id].name then
938 -- if already queued for this slot, remove from queue
939 TrinketMenu.Queue[which] = nil
940 getglobal("TrinketMenu_Trinket"..which.."Queue"):Hide()
941 else
942 if TrinketMenu.Queue[1-which]==TrinketMenu.BaggedTrinkets[id].name then
943 -- if this was queued for other slot, move to this one
944 TrinketMenu.Queue[1-which] = nil
945 getglobal("TrinketMenu_Trinket"..(1-which).."Queue"):Hide()
946 end
947  
948 getglobal("TrinketMenu_Trinket"..which.."Queue"):SetTexture(TrinketMenu.BaggedTrinkets[id].texture)
949 TrinketMenu.Queue[which] = TrinketMenu.BaggedTrinkets[id].name
950 getglobal("TrinketMenu_Trinket"..which.."Queue"):Show()
951 end
952  
953 elseif not TrinketMenu.Swapping then
954  
955 if arg1=="LeftButton" and IsShiftKeyDown() and ChatFrameEditBox:IsVisible() then
956 -- link to chat instead of swap
957 ChatFrameEditBox:Insert(GetContainerItemLink(TrinketMenu.BaggedTrinkets[id].bag,TrinketMenu.BaggedTrinkets[id].slot))
958 elseif cursor_empty() then
959 PickupContainerItem(TrinketMenu.BaggedTrinkets[id].bag,TrinketMenu.BaggedTrinkets[id].slot)
960 if arg1=="LeftButton" then
961 PickupInventoryItem(13)
962 TrinketMenu_Trinket0Icon:SetVertexColor(0.4, 0.4, 0.4)
963 else
964 PickupInventoryItem(14)
965 TrinketMenu_Trinket1Icon:SetVertexColor(0.4, 0.4, 0.4)
966 end
967 TrinketMenu.Swapping = true
968 end
969 end
970  
971 if not IsShiftKeyDown() and TrinketMenuOptions.KeepOpen=="OFF" then
972 TrinketMenu_MenuFrame:Hide()
973 end
974 end
975  
976 --[[ Tooltips ]]--
977  
978 function TrinketMenu_InventoryTooltip()
979  
980 local id = this:GetID()
981  
982 if TrinketMenu_ScalingFrame:IsVisible() or TrinketMenuOptions.ShowTooltips=="OFF" then
983 return
984 end
985  
986 TrinketMenu.TooltipOwner = this
987 TrinketMenu.TooltipType = "INVENTORY"
988 TrinketMenu.TooltipSlot = id
989  
990 TrinketMenu.TooltipBag = TrinketMenu.Queue[id-13]
991  
992 TrinketMenu.TooltipTime = 10 -- immediate update
993 TrinketMenu_TooltipFrame:Show()
994 end
995  
996 function TrinketMenu_BagTooltip()
997  
998 local id = this:GetID()
999  
1000 if TrinketMenu_ScalingFrame:IsVisible() or TrinketMenuOptions.ShowTooltips=="OFF" then
1001 return
1002 end
1003  
1004 TrinketMenu.TooltipOwner = this
1005 TrinketMenu.TooltipType = "BAG"
1006 TrinketMenu.TooltipBag = TrinketMenu.BaggedTrinkets[id].bag
1007 TrinketMenu.TooltipSlot = TrinketMenu.BaggedTrinkets[id].slot
1008  
1009 TrinketMenu.TooltipTime = 10 -- immediate update
1010 TrinketMenu_TooltipFrame:Show()
1011 end
1012  
1013 function TrinketMenu_ClearTooltip()
1014  
1015 GameTooltip:Hide()
1016 TrinketMenu.TooltipType = nil
1017 TrinketMenu_TooltipFrame:Hide()
1018 end
1019  
1020 -- updates the tooltip created in the functions above
1021 function TrinketMenu_TooltipFrame_OnUpdate(arg1)
1022  
1023 TrinketMenu.TooltipTime = TrinketMenu.TooltipTime + arg1
1024 if TrinketMenu.TooltipTime > TrinketMenu.TooltipUpdateTimer then
1025 TrinketMenu.TooltipTime = 0
1026  
1027 if TrinketMenu.TooltipType then
1028  
1029 local cooldown
1030  
1031 if TrinketMenuOptions.TooltipFollow=="ON" then
1032 if TrinketMenu.TooltipOwner:GetLeft()<400 then
1033 GameTooltip:SetOwner(TrinketMenu.TooltipOwner,"ANCHOR_RIGHT")
1034 else
1035 GameTooltip:SetOwner(TrinketMenu.TooltipOwner,"ANCHOR_LEFT")
1036 end
1037 else
1038 GameTooltip_SetDefaultAnchor(GameTooltip,TrinketMenu.TooltipOwner)
1039 end
1040 if TrinketMenu.TooltipType=="BAG" then
1041 GameTooltip:SetBagItem(TrinketMenu.TooltipBag,TrinketMenu.TooltipSlot)
1042 cooldown = GetContainerItemCooldown(TrinketMenu.TooltipBag,TrinketMenu.TooltipSlot)
1043 else
1044 GameTooltip:SetInventoryItem("player",TrinketMenu.TooltipSlot)
1045 cooldown = GetInventoryItemCooldown("player",TrinketMenu.TooltipSlot)
1046 if TrinketMenu.TooltipBag then
1047 GameTooltip:AddLine("Queued: "..TrinketMenu.TooltipBag)
1048 end
1049 end
1050 GameTooltip:Show()
1051 if cooldown==0 then
1052 -- stop updates if this trinket has no cooldown
1053 TrinketMenu.TooltipType = nil
1054 TrinketMenu_TooltipFrame:Hide()
1055 end
1056 end
1057  
1058 end
1059  
1060 end
1061  
1062 -- normal tooltip for options
1063 function TrinketMenu_OnTooltip(arg1,arg2)
1064  
1065 if TrinketMenuOptions.ShowTooltips=="ON" then
1066 GameTooltip_SetDefaultAnchor(GameTooltip,this)
1067 GameTooltip:AddLine(arg1)
1068 GameTooltip:AddLine(arg2,.8,.8,.8,1)
1069 GameTooltip:Show()
1070 end
1071 end
1072  
1073 --[[ Minimap Icon ]]--
1074  
1075 function TrinketMenu_IconDraggingFrame_OnUpdate(arg1)
1076 local xpos,ypos = GetCursorPosition()
1077 local xmin,ymin = Minimap:GetLeft() or 400, Minimap:GetBottom() or 400
1078  
1079 xpos = xmin-xpos/Minimap:GetEffectiveScale()+70
1080 ypos = ypos/Minimap:GetEffectiveScale()-ymin-70
1081  
1082 TrinketMenuOptions.IconPos = math.deg(math.atan2(ypos,xpos))
1083 move_icon()
1084 end
1085  
1086 function TrinketMenu_IconFrame_OnClick(arg1)
1087  
1088 if arg1=="LeftButton" and TrinketMenuOptions.DisableToggle=="OFF" then
1089 TrinketMenu_Toggle()
1090 else
1091 if TrinketMenu_OptFrame:IsVisible() then
1092 TrinketMenu_OptFrame:Hide()
1093 else
1094 TrinketMenu_OptFrame:Show()
1095 end
1096 end
1097 end
1098  
1099 --[[ Options ]]--
1100  
1101 function TrinketMenu_Opt_OnEnter()
1102  
1103 local id = this:GetName()
1104  
1105 if TrinketMenu.OptInfo[id] then
1106 TrinketMenu_OnTooltip(TrinketMenu.OptInfo[id].text,TrinketMenu.OptInfo[id].tooltip)
1107 end
1108 end
1109  
1110 function TrinketMenu_Opt_OnClick()
1111  
1112 local id_name = this:GetName()
1113 local id_var = TrinketMenu.OptInfo[id_name].info
1114  
1115 if this:GetChecked()==1 then
1116 TrinketMenuOptions[id_var] = "ON"
1117 else
1118 TrinketMenuOptions[id_var] = "OFF"
1119 end
1120  
1121 if id_var=="Locked" then
1122 set_lock(TrinketMenuOptions.Locked)
1123 elseif id_var=="KeepOpen" then
1124 TrinketMenu_MenuFrame:Show()
1125 elseif id_var=="ShowIcon" then
1126 show_icon()
1127 elseif id_var=="CooldownCount" then
1128 TrinketMenu.CooldownCountTime = TrinketMenu.CooldownCountUpdateTimer -- immediate update
1129 cooldown_opts_changed()
1130 elseif id_var=="KeepDocked" then
1131 if TrinketMenuOptions.KeepDocked=="ON" then
1132 dock_windows()
1133 else
1134 TrinketMenu.FrameToScale = TrinketMenu_MenuFrame
1135 TrinketMenu_ScaleFrame(TrinketMenu_MenuFrame:GetScale())
1136 end
1137  
1138 TrinketMenu.FrameToScale = this:GetParent()
1139 TrinketMenu.ScalingWidth = this:GetParent():GetWidth()
1140 elseif id_var=="Notify" then
1141 cooldown_opts_changed()
1142 elseif id_var=="SquareMinimap" then
1143 move_icon()
1144 end
1145  
1146 subopt_enable("ShowIcon","DisableToggle")
1147 subopt_enable("Notify","NotifyUsedOnly")
1148 subopt_enable("Notify","NotifyChatAlso")
1149 subopt_enable("Notify","NotifyThirty")
1150 subopt_enable("ShowTooltips","TooltipFollow")
1151 subopt_enable("ShowIcon","SquareMinimap")
1152 end
1153  
1154 function TrinketMenu_Opt_Reset()
1155  
1156 TrinketMenuOptions = {
1157 CooldownCount="OFF", TooltipFollow="OFF", KeepOpen="OFF", ShowIcon="ON",
1158 IconPos=-100, Locked="OFF",
1159 KeepDocked="ON", Notify="OFF", -- 2.1
1160 DisableToggle="OFF", NotifyUsedOnly="OFF", NotifyChatAlso="OFF" -- 2.2
1161 }
1162 TrinketMenuPerOptions = {
1163 MainDock="BOTTOMRIGHT", MenuDock="BOTTOMLEFT", MainOrient="HORIZONTAL", MenuOrient="VERTICAL",
1164 XPos=400, YPos=400, MainScale=1.0, MenuScale=1.0,
1165 Visible="ON"
1166 }
1167  
1168 TrinketMenu_OptFrame:ClearAllPoints()
1169 TrinketMenu_OptFrame:SetPoint("CENTER","UIParent","CENTER")
1170 initialize_display()
1171  
1172 end
1173  
1174 --[[ Cooldown Counters ]]--
1175  
1176  
1177 local function format_time(seconds)
1178  
1179 if seconds<60 then
1180 return math.floor(seconds+.5).." s"
1181 else
1182 if seconds < 3600 then
1183 return math.ceil((seconds/60)).." m"
1184 else
1185 return math.ceil((seconds/3600)).." h"
1186 end
1187 end
1188  
1189 end
1190  
1191 -- indexed by TrinketMenuOptions.NotifyThirty
1192 local ready_text = { ["ON"] = " ready soon!", ["OFF"] = " ready!" }
1193  
1194 -- sends a message "(trinket) ready!"
1195 local function notify(trinket)
1196  
1197 if trinket and ((TrinketMenu.NotifyList[trinket] and TrinketMenuOptions.NotifyUsedOnly=="ON") or TrinketMenuOptions.NotifyUsedOnly=="OFF") then
1198 if SCT_CmdDisplay then
1199 -- send via SCT if it exists
1200 SCT_CmdDisplay("'"..string.gsub(trinket,"'","")..ready_text[TrinketMenuOptions.NotifyThirty].."' 2 7 9")
1201 else
1202 -- send vis UIErrorsFrame if SCT doesn't exit
1203 UIErrorsFrame:AddMessage(trinket..ready_text[TrinketMenuOptions.NotifyThirty],.2,.7,.9,1,UIERRORS_HOLD_TIME)
1204 end
1205  
1206 if TrinketMenuOptions.NotifyChatAlso=="ON" then
1207 DEFAULT_CHAT_FRAME:AddMessage("|cff33b2e5"..trinket..ready_text[TrinketMenuOptions.NotifyThirty])
1208 end
1209 TrinketMenu.NotifyList[trinket] = nil
1210 PlaySound("GnomeExploration")
1211 end
1212 end
1213  
1214 local function write_cooldown(where,start,duration)
1215  
1216 local cooldown = duration - (TrinketMenu.CurrentTime - start)
1217  
1218 if start==0 then
1219 where:SetText("")
1220 elseif cooldown<3 and not where:GetText() then
1221 -- this is a global cooldown. don't display it. not accurate but at least not annoying
1222 else
1223 where:SetText(format_time(cooldown))
1224  
1225 -- placed here because we don't want to be notified on global cooldowns
1226 if TrinketMenuOptions.Notify=="ON" and ((TrinketMenuOptions.NotifyThirty=="OFF" and cooldown<1) or (TrinketMenuOptions.NotifyThirty=="ON" and (cooldown>30 and cooldown<=31))) then
1227 local _,_,id = string.find(where:GetName(),"TrinketMenu_Menu(%d+)Time")
1228 if id then
1229 notify(TrinketMenu.BaggedTrinkets[tonumber(id)].name)
1230 else
1231 if where==TrinketMenu_Trinket0Time then
1232 id = trinket_name(0)
1233 if id then
1234 notify(id)
1235 end
1236 else
1237 id = trinket_name(1)
1238 if id then
1239 notify(id)
1240 end
1241 end
1242 end
1243 end
1244 end
1245 end
1246  
1247 function TrinketMenu_CooldownCountFrame_OnUpdate(arg1)
1248  
1249 TrinketMenu.CooldownCountTime = TrinketMenu.CooldownCountTime + arg1
1250 if TrinketMenu.CooldownCountTime > TrinketMenu.CooldownCountUpdateTimer then
1251 -- update cooldowns
1252 TrinketMenu.CooldownCountTime = 0
1253  
1254 if TrinketMenuOptions.CooldownCount=="ON" or TrinketMenuOptions.Notify=="ON" then
1255  
1256 local i,start,duration
1257 TrinketMenu.CurrentTime = GetTime()
1258  
1259 if TrinketMenu_MainFrame:IsVisible() then
1260 start, duration = GetInventoryItemCooldown("player",13)
1261 write_cooldown(TrinketMenu_Trinket0Time,start,duration)
1262 start, duration = GetInventoryItemCooldown("player",14)
1263 write_cooldown(TrinketMenu_Trinket1Time,start,duration)
1264 end
1265  
1266 if TrinketMenu_MenuFrame:IsVisible() or TrinketMenuOptions.Notify=="ON" then
1267 for i=1,TrinketMenu.NumberOfTrinkets do
1268 start, duration = GetContainerItemCooldown(TrinketMenu.BaggedTrinkets[i].bag,TrinketMenu.BaggedTrinkets[i].slot)
1269 write_cooldown(getglobal("TrinketMenu_Menu"..i.."Time"),start,duration)
1270 end
1271 end
1272 end
1273  
1274 end
1275  
1276 end
1277  
1278 function TrinketMenu_CooldownCountFrame_OnHide()
1279  
1280 local i
1281  
1282 TrinketMenu_Trinket0Time:SetText("")
1283 TrinketMenu_Trinket1Time:SetText("")
1284  
1285 for i=1,TrinketMenu.MaxTrinkets do
1286 getglobal("TrinketMenu_Menu"..i.."Time"):SetText("")
1287 end
1288 end