Quantcast
Hooking Mixins and unnamed frames - WoWInterface
Thread Tools Display Modes
09-25-18, 10:34 AM   #1
MuffinManKen
A Flamescale Wyrmkin
AddOn Author - Click to view addons
Join Date: Dec 2009
Posts: 102
Hooking Mixins and unnamed frames

I'm trying to hook WorldMapBountyBoardMixin:ShowBountyTooltip. There was a thread a little while back (http://www.wowinterface.com/forums/s...ad.php?t=56578) that I used for reference and what I took from it is that if I hook the mixin AFTER the mixin is created but BEFORE it's used on a frame, the hook will work. Looking at the WorldMap code I didn't believe this was the case, but I tested it anyway with this:
Lua Code:
  1. hooksecurefunc(WorldMapBountyBoardMixin, "ShowBountyTooltip", function(self,bountyIndex)
  2.     print("WorldMapBountyBoardMixin:ShowBountyTooltip " .. tostring(bountyIndex))
  3. end)

The print did not fire. The other method mentioned in that thread is to hook the frame itself, but in this case the frames are unnamed (just a hex string) so I don't believe I can do that directly.

So in a case like this, what is a reliable way to hook the method?
  Reply With Quote
09-25-18, 02:43 PM   #2
sticklord
A Wyrmkin Dreamwalker
AddOn Author - Click to view addons
Join Date: Aug 2014
Posts: 57
Im pretty sure it's impossible to hook the mixin, so you need to hook the frame. Maybe this will work (untested)

Lua Code:
  1. local function ShowBountyTooltip(self, bountyIndex)
  2.     print(bountyIndex)
  3. end
  4.  
  5. for _,frame in pairs({WorldMapFrame:GetChildren()}) do
  6.     if frame.BountyName then
  7.         hooksecurefunc(frame, "ShowBountyTooltip", ShowBountyTooltip)
  8.     end
  9. end

Last edited by sticklord : 09-25-18 at 02:49 PM.
  Reply With Quote
09-25-18, 09:48 PM   #3
MuffinManKen
A Flamescale Wyrmkin
AddOn Author - Click to view addons
Join Date: Dec 2009
Posts: 102
Thanks for the idea, I'll play with this a bit and see how it goes.

Those frames are allocated from a pool on every refresh so that may take some extra fiddling. I'm not entirely sure what happens to the innards of a frame when it's released/acquired. Would the hook stay in place? I guess I'll find out!

Edit: Actually it's the child tabs that are part of the pool, so I think that one issue may be moot.

Last edited by MuffinManKen : 09-25-18 at 10:46 PM.
  Reply With Quote
09-26-18, 10:50 AM   #4
MunkDev
A Scalebane Royal Guard
 
MunkDev's Avatar
AddOn Author - Click to view addons
Join Date: Mar 2015
Posts: 427
WorldMapFrame loads before any of your addons, so you'll need to address its overlay frames directly:
Lua Code:
  1. local function ShowBountyTooltip(self, bountyIndex)
  2.     print("WorldMapBountyBoardMixin:ShowBountyTooltip " .. tostring(bountyIndex))
  3. end
  4.  
  5. for i, frame in ipairs(WorldMapFrame.overlayFrames) do
  6.     if frame.ShowBountyTooltip then
  7.         hooksecurefunc(frame, "ShowBountyTooltip", ShowBountyTooltip)
  8.     end
  9. end
  10.  
  11. hooksecurefunc(WorldMapBountyBoardMixin, "ShowBountyTooltip", ShowBountyTooltip)
__________________
  Reply With Quote
09-26-18, 02:44 PM   #5
MuffinManKen
A Flamescale Wyrmkin
AddOn Author - Click to view addons
Join Date: Dec 2009
Posts: 102
Originally Posted by MunkDev View Post
WorldMapFrame loads before any of your addons, so you'll need to address its overlay frames directly:
That should be bit more efficient than iterating through all of the children. Not that performance should be an issue in this case, but for trivial effort the change seems worthwhile.
  Reply With Quote
09-26-18, 08:28 PM   #6
MuffinManKen
A Flamescale Wyrmkin
AddOn Author - Click to view addons
Join Date: Dec 2009
Posts: 102
In case anyone else is using this API, I'll note here that the factionID returned by GetQuestBountyInfoForMapID is bogus. Sometimes it's an unrelated faction, other times it's 0.

The questID is valid. I use that in a lookup to find the real faction id.
  Reply With Quote
09-26-18, 09:09 PM   #7
MuffinManKen
A Flamescale Wyrmkin
AddOn Author - Click to view addons
Join Date: Dec 2009
Posts: 102
Everything is now working well...almost. Since my hook runs after ShowBountyTooltip is done, I expected that it would be the last line and sometimes it is. But the last thing Blizzard function does is add the Reward and I guess it's a deferred call, so sometimes my line get added in the middle of the rewards like:
Rewards
You are now Friendly with the Champions of Azeroth (my text)
Radiant Azerite Fragment

I tried preloading the rewards (C_TaskQuest.RequestPreloadRewardData(questID)) but that didn't help. My hook is just:
Lua Code:
  1. local msg = "stuff"
  2. WorldMapTooltip:AddLine(msg);
  3. WorldMapTooltip:Show();

The only thing I can think of is to Clear the tooltip and completely duplicate all of Blizzard's code, but that would be kind of awful, wouldn't it?
  Reply With Quote
09-28-18, 03:43 PM   #8
MuffinManKen
A Flamescale Wyrmkin
AddOn Author - Click to view addons
Join Date: Dec 2009
Posts: 102
I ended up clearing and duplicating WoW's code. I feel a little dirty, but it's not like this code is performance critical so I suppose it's good enough.
  Reply With Quote

WoWInterface » Developer Discussions » Lua/XML Help » Hooking Mixins and unnamed frames

Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

vB code is On
Smilies are On
[IMG] code is On
HTML code is Off