WoWInterface

WoWInterface (http://www.wowinterface.com/forums/index.php)
-   MoP archived threads (http://www.wowinterface.com/forums/forumdisplay.php?f=162)
-   -   StanceButton1 taint in nMainbar (http://www.wowinterface.com/forums/showthread.php?t=43746)

ballagarba 07-19-12 04:59 AM

StanceButton1 taint in nMainbar
 
So, Blizzard was kind enough introduce StanceButton1:SetPoint(...) inside StanceBar.lua:StanceBar_Update() :(

Code:

function StanceBar_Update ()
    local numForms = GetNumShapeshiftForms();
    if ( numForms > 0 and not IsPossessBarVisible()) then
        --Setup the Stance bar to display the appropriate number of slots
        if ( numForms == 1 ) then
                        StanceBarMiddle:Hide();
                        StanceBarRight:SetPoint("LEFT", "StanceBarLeft", "LEFT", 12, 0);
                        StanceButton1:SetPoint("BOTTOMLEFT", "StanceBarFrame", "BOTTOMLEFT", 12, 3);
        elseif ( numForms == 2 ) then
                        StanceBarMiddle:Hide();
                        StanceBarRight:SetPoint("LEFT", "StanceBarLeft", "RIGHT", 0, 0);
        else
            StanceBarMiddle:Show();
            StanceBarMiddle:SetPoint("LEFT", "StanceBarLeft", "RIGHT", 0, 0);
            StanceBarMiddle:SetWidth(37 * (numForms-2));
            StanceBarMiddle:SetTexCoord(0, numForms-2, 0, 1);
            StanceBarRight:SetPoint("LEFT", "StanceBarMiddle", "RIGHT", 0, 0);
        end

        StanceBarFrame:Show();
        StanceBar_UpdateState();
    else
        StanceBarFrame:Hide();
    end
    UIParent_ManageFramePositions();
end

The problem I'm having is that I set StanceButton1:SetMovable(true) and StanceButton1:SetUserPlaced(true). However, StanceBar_Update() gets executed after whatever code that does user placement rendering it useless.

So I tried a couple of hacks to prevent StanceBar_Update() from moving StanceButton1:

1. I just override Blizzard's function, however this obviously caused taint issues.

lua Code:
  1. function StanceBar_Update()
  2.     local numForms = GetNumShapeshiftForms()
  3.     if (numForms > 0 and not IsPossessBarVisible()) then
  4.         StanceBarFrame:Show()
  5.         securecall('StanceBar_UpdateState')
  6.     else
  7.         StanceBarFrame:Hide()
  8.     end
  9.     securecall('UIParent_ManageFramePositions')
  10. end

2. I figured I could force the statement numForms == 1 to always be false, because that's the only time they re-position. I figured this was a golden solution, however, it also caused taint :(

lua Code:
  1. StanceBarFrame.numForms = GetNumShapeshiftForms()

3. Now I tried to save the position of StanceButton1 before StanceBar_Update() moves it, and do a hooksecurefunc('StanceBar_Update', ...) and move it after that. Also taint, apparently, you can't do StanceButton1:ClearAllPoints() from inside that hook (WTF?):

lua Code:
  1. local point, relativeTo, relativePoint, xOffset, yOffset = StanceButton1:GetPoint()
  2. hooksecurefunc('StanceBar_Update', function()
  3.     if (GetNumShapeshiftForms() == 1) then
  4.         StanceButton1:ClearAllPoints()
  5.         StanceButton1:SetPoint(point, relativeTo, relativePoint, xOffset, yOffset)
  6.     end
  7. end

4. Next, I came up with the idea of just calling StanceBar_Update() immediately in my code to have it execute before the user position got set. This oddly enough also caused taint :confused:

lua Code:
  1. securecall('StanceBar_Update')

5. This works, but is ugly as hell and some quirks appear from time to time:

lua Code:
  1. local point, relativeTo, relativePoint, xOffset, yOffset
  2.  
  3. local f = CreateFrame('Frame')
  4. f:RegisterEvent('VARIABLES_LOADED')
  5. f:RegisterEvent('PLAYER_ALIVE')
  6. f:SetScript('OnEvent', function(self, event, ...)
  7.     if (event == 'VARIABLES_LOADED') then
  8.         point, relativeTo, relativePoint, xOffset, yOffset = StanceButton1:GetPoint()
  9.         self:UnregisterEvent('VARIABLES_LOADED')
  10.     end
  11.  
  12.     if (event == 'PLAYER_ALIVE') then
  13.         if (point) then
  14.             StanceButton1:ClearAllPoints()
  15.             StanceButton1:SetPoint(point, relativeTo, relativePoint, xOffset, yOffset)
  16.         end
  17.         self:UnregisterEvent('PLAYER_ALIVE')
  18.     end
  19. end)

The taint causes a interface blocked action thingie when trying to do action bar switching when in combat, and blocked it from switching. Anyone have any thoughts? I find it weird that StanceButton1:ClearAllPoints() sometimes causes taint, and sometimes it doesn't.

Oh yeah, the addon is nMainbar and here's the MoP source:
https://github.com/renstrom/NeavUI/b.../stancebar.lua.

Torhal 07-19-12 10:31 AM

You didn't try using hooksecurefunc() by chance, did you?

ballagarba 07-19-12 10:53 AM

Quote:

Originally Posted by Torhal (Post 258431)
You didn't try using hooksecurefunc() by chance, did you?

Yeah I did:

Quote:

Originally Posted by ballagarba (Post 258415)
3. Now I tried to save the position of StanceButton1 before StanceBar_Update() moves it, and do a hooksecurefunc('StanceBar_Update', ...) and move it back. Also taints, apparently, you can't do StanceButton1:ClearAllPoints() from inside that hook (WTF?):

lua Code:
  1. local point, relativeTo, relativePoint, xOffset, yOffset = StanceButton1:GetPoint()
  2. hooksecurefunc('StanceBar_Update', function()
  3.     if (GetNumShapeshiftForms() == 1) then
  4.         StanceButton1:ClearAllPoints()
  5.         StanceButton1:SetPoint(point, relativeTo, relativePoint, xOffset, yOffset)
  6.     end
  7. end

However, I don't see how that would work seeing as when the hook runs I have no idea of knowing what StanceButton1 had for position before the original function (StanceBar_Update()) moved it. I could just move it, but the point is that I want it to be user placed, so I can't move it programmatically like that unless I could somehow fetch that information from layout-local.txt.

Lombra 07-19-12 12:13 PM

Can you not move the entire StanceBar instead?

ballagarba 07-19-12 12:45 PM

Quote:

Originally Posted by Lombra (Post 258442)
Can you not move the entire StanceBar instead?

Hmm, came up with this and it actually seems to work nicely :D

lua Code:
  1. if (GetNumShapeshiftForms() == 1) then
  2.     StanceBarFrame:SetMovable(true)
  3.     StanceBarFrame:SetUserPlaced(true)
  4.     StanceButton1:HookScript('OnDragStop', function(self)
  5.         local point, relativeTo, relativePoint, xOffset, yOffset = self:GetPoint()
  6.         StanceBarFrame:ClearAllPoints()
  7.         -- 12 and 3 is to offset for StanceButton1's relative position towards StanceBarFrame
  8.         StanceBarFrame:SetPoint(point, relativeTo, relativePoint, xOffset - 12, yOffset - 3)
  9.     end)
  10. end

zork 07-20-12 09:56 AM

Will not work either. On bars with only one form the StanceButton1 will always reset. Thus you have to actually reparent the StanceBarFrame.

My full solution is here:
http://code.google.com/p/rothui/sour.../stancebar.lua

I have a new frame that the stancebar is reparented to. On unlocking a dragFrame will show up on a pretty high framelevel thus overlaying all the other frames. The drag event is delegated to the frame in the bottom thus the bottom frame will move.

ballagarba 07-20-12 10:17 AM

Quote:

Originally Posted by zork (Post 258497)
Will not work either. On bars with only one form the StanceButton1 will always reset. Thus you have to actually reparent the StanceBarFrame.

My full solution is here:
http://code.google.com/p/rothui/sour.../stancebar.lua

I have a new frame that the stancebar is reparented to. On unlocking a dragFrame will show up on a pretty high framelevel thus overlaying all the other frames. The drag event is delegated to the frame in the bottom thus the bottom frame will move.

Well that's pretty much what I'm doing. As I've also said, this is only a problem when GetNumShapeshiftForms() == 1. Therefore I made StanceBarFrame movable as well, and when the user drags the StanceButton1 to whatever position they prefer, I update the StanceBarFrame position as well via HookScript('OnDragStop', ...) on StanceButton1 and off-setting with y and x values available in StanceBar_Update() (12 and 3 respectively).

Since Blizzard doesn't re-anchor StanceBarFrame like they do StanceButton1, when they run StanceBar_Update() it will just anchor StanceButton1 to whatever user position StanceBarFrame has.

Plus I can't have an overlay show up every time the user presses alt+shift (I'm not using slash commands).

ballagarba 07-29-12 05:19 AM

So it seems like as of build 15913 Blizzard is no longer moving the StanceButton1 inside the StanceBar_Update() function when GetNumShapeshiftForms() == 1 :banana:

https://github.com/p3lim/wow-ui-sour...99afb4f7#L75L5

zork 07-29-12 05:25 AM

... how nice.

I can confirm that. Updated my version of rActionBarStyler already.


All times are GMT -6. The time now is 02:08 PM.

vBulletin © 2014, Jelsoft Enterprises Ltd
©2012 ZAM Network LLC