Thread Tools Display Modes
08-18-17, 07:07 PM   #1
frohanss
A Cyclonian
AddOn Author - Click to view addons
Join Date: Mar 2011
Posts: 40
Question Macro button inside bag, and still can be opened in combat

Hello

So i have my edited version of Stuffing bags.
I have added 3 buttons inside it for depositing regents, 2x sort options and a button to use any artifact power items in the bags.

Since macro button needs "SecureActionButtonTemplate", the bags can't be opened during combat.

Any good sugestion on how to fix this?
It's fine if the buttons can't be used during combat, just as longe the bags will open.

Lua Code:
  1. function Stuffing:InitBags()
  2.     if self.frame then return end
  3.  
  4.     self.buttons = {}
  5.     self.bags = {}
  6.     self.bagframe_buttons = {}
  7.  
  8.     local f = self:CreateBagFrame("Bags")
  9.     f:SetScript("OnShow", Stuffing_OnShow)
  10.     f:SetScript("OnHide", Stuffing_OnHide)
  11.  
  12.     local editbox = CreateFrame("EditBox", nil, f)
  13.     editbox:Hide()
  14.     editbox:SetAutoFocus(true)
  15.     editbox:SetHeight(32)
  16.     editbox:CreateBackdrop("Default")
  17.     editbox.backdrop:SetPoint("TOPLEFT", -2, 1)
  18.     editbox.backdrop:SetPoint("BOTTOMRIGHT", 2, -1)
  19.  
  20.     local resetAndClear = function(self)
  21.         self:GetParent().detail:Show()
  22.         self:ClearFocus()
  23.         Stuffing:SearchReset()
  24.     end
  25.  
  26.     local updateSearch = function(self, t)
  27.         if t == true then
  28.             Stuffing:SearchUpdate(self:GetText())
  29.         end
  30.     end
  31.  
  32.     editbox:SetScript("OnEscapePressed", resetAndClear)
  33.     editbox:SetScript("OnEnterPressed", resetAndClear)
  34.     editbox:SetScript("OnEditFocusLost", editbox.Hide)
  35.     editbox:SetScript("OnEditFocusGained", editbox.HighlightText)
  36.     editbox:SetScript("OnTextChanged", updateSearch)
  37.     editbox:SetText(SEARCH)
  38.  
  39.     local detail = f:CreateFontString(nil, "ARTWORK", "GameFontHighlightLarge")
  40.     detail:SetPoint("TOPLEFT", f, 11, -10)
  41.     detail:SetPoint("RIGHT", f, -140, -10)
  42.     detail:SetHeight(13)
  43.     detail:SetShadowColor(0, 0, 0, 0)
  44.     detail:SetJustifyH("LEFT")
  45.     detail:SetText("|cff9999ff"..SEARCH.."|r")
  46.     editbox:SetAllPoints(detail)
  47.  
  48.     local button = CreateFrame("Button", nil, f)
  49.     button:EnableMouse(true)
  50.     button:RegisterForClicks("LeftButtonUp", "RightButtonUp")
  51.     button:SetAllPoints(detail)
  52.     button.ttText = L_BAG_RIGHT_CLICK_SEARCH
  53.     button:SetScript("OnClick", function(self, btn)
  54.         if btn == "RightButton" then
  55.             self:GetParent().detail:Hide()
  56.             self:GetParent().editbox:Show()
  57.             self:GetParent().editbox:HighlightText()
  58.         else
  59.             if self:GetParent().editbox:IsShown() then
  60.                 self:GetParent().editbox:Hide()
  61.                 self:GetParent().editbox:ClearFocus()
  62.                 self:GetParent().detail:Show()
  63.                 Stuffing:SearchReset()
  64.             end
  65.         end
  66.     end)
  67.  
  68.     local tooltip_hide = function()
  69.         GameTooltip:Hide()
  70.     end
  71.  
  72.     local tooltip_show = function(self)
  73.         GameTooltip:SetOwner(self, "ANCHOR_CURSOR")
  74.         GameTooltip:ClearLines()
  75.         GameTooltip:SetText(self.ttText)
  76.     end
  77.  
  78.     button:SetScript("OnEnter", tooltip_show)
  79.     button:SetScript("OnLeave", tooltip_hide)
  80.    
  81.     --Deposit Button
  82.     f.depositButton = CreateFrame("Button", nil, f);
  83.     f.depositButton:SetSize(16, 16)
  84.     f.depositButton:SetTemplate()
  85.     f.depositButton:SetPoint("TOPRIGHT", f, -25, -4)
  86.     f.depositButton:SetHeight(18)
  87.     f.depositButton:SetWidth(18)
  88.     f.depositButton:SetNormalTexture("Interface\\ICONS\\misc_arrowdown")
  89.     f.depositButton:GetNormalTexture():SetTexCoord(0.1, 0.9, 0.1, 0.9)
  90.     f.depositButton:GetNormalTexture():SetPoint("TOPLEFT", 2, -2)
  91.     f.depositButton:GetNormalTexture():SetPoint("BOTTOMRIGHT", -2, 2)
  92.     f.depositButton:SetPushedTexture("Interface\\ICONS\\misc_arrowdown")
  93.     f.depositButton:GetPushedTexture():SetTexCoord(0.1, 0.9, 0.1, 0.9)
  94.     f.depositButton:GetPushedTexture():SetPoint("TOPLEFT", 2, -2)
  95.     f.depositButton:GetPushedTexture():SetPoint("BOTTOMRIGHT", -2, 2)
  96.     f.depositButton:StyleButton()
  97.     f.depositButton.ttText = "Deposit Reagents"
  98.     f.depositButton:SetScript("OnEnter", tooltip_show)
  99.     f.depositButton:SetScript("OnLeave", tooltip_hide)
  100.     f.depositButton:SetScript('OnClick',function(self, btn)
  101.  
  102.             PlaySound("igMainMenuOption");
  103.             DepositReagentBank()
  104.     end)
  105.    
  106.     --Sort Button
  107.     f.sortButton = CreateFrame("Button", nil, f, "SecureActionButtonTemplate");
  108.     f.sortButton:SetSize(16, 16)
  109.     f.sortButton:SetTemplate()
  110.     f.sortButton:SetPoint("TOPRIGHT", f.depositButton, -25, 0)
  111.     f.sortButton:SetHeight(18)
  112.     f.sortButton:SetWidth(18)
  113.     f.sortButton:SetNormalTexture("Interface\\ICONS\\INV_Pet_Broom")
  114.     f.sortButton:GetNormalTexture():SetTexCoord(0.1, 0.9, 0.1, 0.9)
  115.     f.sortButton:GetNormalTexture():SetPoint("TOPLEFT", 2, -2)
  116.     f.sortButton:GetNormalTexture():SetPoint("BOTTOMRIGHT", -2, 2)
  117.     f.sortButton:SetPushedTexture("Interface\\ICONS\\INV_Pet_Broom")
  118.     f.sortButton:GetPushedTexture():SetTexCoord(0.1, 0.9, 0.1, 0.9)
  119.     f.sortButton:GetPushedTexture():SetPoint("TOPLEFT", 2, -2)
  120.     f.sortButton:GetPushedTexture():SetPoint("BOTTOMRIGHT", -2, 2)
  121.     f.sortButton:StyleButton()
  122.     f.sortButton.ttText = "LM:Cleanup / RM:Blizzard"
  123.     f.sortButton:SetScript("OnEnter", tooltip_show)
  124.     f.sortButton:SetScript("OnLeave", tooltip_hide)
  125.     f.sortButton:SetScript("OnMouseUp", function(self, btn)
  126.         if IsShiftKeyDown() then
  127.         ToggleAchievementFrame()
  128.         elseif btn == "RightButton" then
  129.         SetSortBagsRightToLeft(true)
  130.         SortBags()
  131.         else
  132.         f.sortButton:SetAttribute("type1", "macro")
  133.         f.sortButton:SetAttribute('macrotext', '/bags sort d')
  134.         end
  135.     end)
  136.    
  137.     --Artifact Button
  138.     f.ArtifactButton = CreateFrame("Button", nil, f, "SecureActionButtonTemplate");
  139.     f.ArtifactButton:SetSize(16, 16)
  140.     f.ArtifactButton:SetTemplate()
  141.     f.ArtifactButton:SetPoint("TOPRIGHT", f.sortButton, -25, 0)
  142.     f.ArtifactButton:SetHeight(18)
  143.     f.ArtifactButton:SetWidth(18)
  144.     f.ArtifactButton:SetNormalTexture("Interface\\Icons\\Achievement_doublejeopardy")
  145.     f.ArtifactButton:GetNormalTexture():SetTexCoord(0.1, 0.9, 0.1, 0.9)
  146.     f.ArtifactButton:GetNormalTexture():SetPoint("TOPLEFT", 2, -2)
  147.     f.ArtifactButton:GetNormalTexture():SetPoint("BOTTOMRIGHT", -2, 2)
  148.     f.ArtifactButton:SetPushedTexture("Interface\\ICONS\\INV_Pet_Broom")
  149.     f.ArtifactButton:GetPushedTexture():SetTexCoord(0.1, 0.9, 0.1, 0.9)
  150.     f.ArtifactButton:GetPushedTexture():SetPoint("TOPLEFT", 2, -2)
  151.     f.ArtifactButton:GetPushedTexture():SetPoint("BOTTOMRIGHT", -2, 2)
  152.     f.ArtifactButton:StyleButton()
  153.     f.ArtifactButton.ttText = "Use Artifact Power item in bag"
  154.     f.ArtifactButton:SetScript("OnEnter", tooltip_show)
  155.     f.ArtifactButton:SetScript("OnLeave", tooltip_hide)
  156.     f.ArtifactButton:SetScript("OnMouseUp", function(self, btn)
  157.  
  158.         f.ArtifactButton:SetAttribute("type", "macro")
  159.         f.ArtifactButton:SetAttribute('macrotext', '/run local b=ApB or CreateFrame("Button","ApB",nil,"SecureActionButtonTemplate") for i=0,4 do for j=1,32 do if IsArtifactPowerItem(GetContainerItemID(i,j)) then b:SetAttribute("item",i.." "..j) b:SetAttribute("type","item") return end end end \n/click ApB')
  160.     end)
  161.    
  162.     f.editbox = editbox
  163.     f.detail = detail
  164.     f.button = button
  165.     self.frame = f
  166.     f:Hide()
  167. end
  Reply With Quote
08-18-17, 07:33 PM   #2
MunkDev
A Scalebane Royal Guard
 
MunkDev's Avatar
AddOn Author - Click to view addons
Join Date: Mar 2015
Posts: 431
The real question is why you're using SecureActionButtonTemplate in the first place since the commands you're using in those macros are not secure.
Just write the code directly in an OnClick script instead.
__________________
  Reply With Quote
08-18-17, 07:47 PM   #3
frohanss
A Cyclonian
AddOn Author - Click to view addons
Join Date: Mar 2011
Posts: 40
Originally Posted by MunkDev View Post
The real question is why you're using SecureActionButtonTemplate in the first place since the commands you're using in those macros are not secure.
Just write the code directly in an OnClick script instead.
Maybe im just tired here but, not sure how to make it for the code with 2 macros for using the artifact items.
  Reply With Quote
08-18-17, 07:51 PM   #4
MunkDev
A Scalebane Royal Guard
 
MunkDev's Avatar
AddOn Author - Click to view addons
Join Date: Mar 2015
Posts: 431
It's simple really, just call UseContainerItem(bag, slot) directly in your script. Some functions are protected, yes, but some are only protected in the sense that they need to come from a hardware event. Calling the function inside an OnClick script means that you clicked on the button with your mouse to use it, so it should be okay.
__________________
  Reply With Quote
08-18-17, 08:00 PM   #5
frohanss
A Cyclonian
AddOn Author - Click to view addons
Join Date: Mar 2011
Posts: 40
Originally Posted by MunkDev View Post
It's simple really, just call UseContainerItem(bag, slot) directly in your script. Some functions are protected, yes, but some are only protected in the sense that they need to come from a hardware event. Calling the function inside an OnClick script means that you clicked on the button with your mouse to use it, so it should be okay.
hmm ok Been away from lua for a year so rusty.
Mainly used OnClick to use toggle frames like ToggleAchievementFrame()
  Reply With Quote
08-18-17, 08:03 PM   #6
MunkDev
A Scalebane Royal Guard
 
MunkDev's Avatar
AddOn Author - Click to view addons
Join Date: Mar 2015
Posts: 431
By the way, bags can have up to 36 slots, not 32. Even so, you're better off using a dynamic approach when looping through the bags.
Lua Code:
  1. for bag=0, 4 do
  2.     for slot=1, GetContainerNumSlots(bag) do
  3.         -- do something
  4.     end
  5. end
__________________
  Reply With Quote
08-18-17, 08:33 PM   #7
frohanss
A Cyclonian
AddOn Author - Click to view addons
Join Date: Mar 2011
Posts: 40
Originally Posted by MunkDev View Post
By the way, bags can have up to 36 slots, not 32. Even so, you're better off using a dynamic approach when looping through the bags.
Lua Code:
  1. for bag=0, 4 do
  2.     for slot=1, GetContainerNumSlots(bag) do
  3.         -- do something
  4.     end
  5. end
No luck with

Lua Code:
  1. f.ArtifactButton:SetScript('OnClick',function(self, btn)
  2.         for bag=0, 4 do
  3.             for slot=1, GetContainerNumSlots(bag) do
  4.                 if IsArtifactPowerItem(GetContainerItemID(bag, slot)) then UseContainerItem(bag, slot)
  5.             end
  6.         end
  7.     end)
  Reply With Quote
08-18-17, 09:01 PM   #8
MunkDev
A Scalebane Royal Guard
 
MunkDev's Avatar
AddOn Author - Click to view addons
Join Date: Mar 2015
Posts: 431
Lua Code:
  1. f.ArtifactButton:SetScript('OnClick',function(self, btn)
  2.     for bag=0, 4 do
  3.         for slot=1, GetContainerNumSlots(bag) do
  4.             if IsArtifactPowerItem(GetContainerItemID(bag, slot)) then
  5.                 return UseContainerItem(bag, slot)
  6.             end
  7.         end
  8.     end
  9. end)

If that doesn't work, just inherit your button from ContainerFrameItemButtonTemplate and set the IDs in a PreClick script and use the inherited OnClick. That requires the parent of your button to have the bag ID and the button itself to have the slot ID. Bag buttons are not protected, but if you're getting a taint error it just means that the call to UseContainerItem needs to come from an untainted function.

Lua Code:
  1. f.ArtifactButton:SetScript('PreClick',function(self, btn)
  2.     for bag=0, 4 do
  3.         for slot=1, GetContainerNumSlots(bag) do
  4.             if IsArtifactPowerItem(GetContainerItemID(bag, slot)) then
  5.                 self:GetParent():SetID(bag)
  6.                 self:SetID(slot)
  7.                 return
  8.             end
  9.         end
  10.     end
  11. end)
__________________

Last edited by MunkDev : 08-18-17 at 09:31 PM.
  Reply With Quote
08-19-17, 04:10 AM   #9
frohanss
A Cyclonian
AddOn Author - Click to view addons
Join Date: Mar 2011
Posts: 40
Originally Posted by MunkDev View Post
Lua Code:
  1. f.ArtifactButton:SetScript('OnClick',function(self, btn)
  2.     for bag=0, 4 do
  3.         for slot=1, GetContainerNumSlots(bag) do
  4.             if IsArtifactPowerItem(GetContainerItemID(bag, slot)) then
  5.                 return UseContainerItem(bag, slot)
  6.             end
  7.         end
  8.     end
  9. end)

If that doesn't work, just inherit your button from ContainerFrameItemButtonTemplate and set the IDs in a PreClick script and use the inherited OnClick. That requires the parent of your button to have the bag ID and the button itself to have the slot ID. Bag buttons are not protected, but if you're getting a taint error it just means that the call to UseContainerItem needs to come from an untainted function.

Lua Code:
  1. f.ArtifactButton:SetScript('PreClick',function(self, btn)
  2.     for bag=0, 4 do
  3.         for slot=1, GetContainerNumSlots(bag) do
  4.             if IsArtifactPowerItem(GetContainerItemID(bag, slot)) then
  5.                 self:GetParent():SetID(bag)
  6.                 self:SetID(slot)
  7.                 return
  8.             end
  9.         end
  10.     end
  11. end)
Thanks alot for the help
Seems like i need to use preclick, the first one triggered protected code.
Never used preclick before. Behaves a bit strange, left click picks up the item and right click uses the item and there is no tooltip showing. Can it be changed to both show tooltip and also have anyclick use the items instead of picking it up?

Lua Code:
  1. --Artifact Button
  2.     f.ArtifactButton = CreateFrame("Button", nil, f, "BankItemButtonGenericTemplate");
  3.     f.ArtifactButton:SetSize(16, 16)
  4.     f.ArtifactButton:SetTemplate()
  5.     f.ArtifactButton:SetPoint("TOPRIGHT", f.sortButton, -25, 0)
  6.     f.ArtifactButton:SetHeight(18)
  7.     f.ArtifactButton:SetWidth(18)
  8.     f.ArtifactButton:SetNormalTexture("Interface\\Icons\\Achievement_doublejeopardy")
  9.     f.ArtifactButton:GetNormalTexture():SetTexCoord(0.1, 0.9, 0.1, 0.9)
  10.     f.ArtifactButton:GetNormalTexture():SetPoint("TOPLEFT", 2, -2)
  11.     f.ArtifactButton:GetNormalTexture():SetPoint("BOTTOMRIGHT", -2, 2)
  12.     f.ArtifactButton:StyleButton()
  13.     f.ArtifactButton.ttText = "Use Artifact Power item in bag"
  14.     f.ArtifactButton:SetScript("OnEnter", tooltip_show)
  15.     f.ArtifactButton:SetScript("OnLeave", tooltip_hide)
  16.     f.ArtifactButton:SetScript('PreClick',function(self, btn)
  17.         for bag=0, 4 do
  18.             for slot=1, GetContainerNumSlots(bag) do
  19.                 if IsArtifactPowerItem(GetContainerItemID(bag, slot)) then
  20.                     self:GetParent():SetID(bag)
  21.                     self:SetID(slot)
  22.                     return
  23.                 end
  24.             end
  25.         end
  26.     end)
  Reply With Quote
08-20-17, 04:33 AM   #10
MunkDev
A Scalebane Royal Guard
 
MunkDev's Avatar
AddOn Author - Click to view addons
Join Date: Mar 2015
Posts: 431
If you haven't already, download the source code and you can look at these things by examining the templates.

The OnClick function (ContainerFrameItemButton_OnClick) uses LeftButton for pickups and any other button for usage. To my knowledge, you can't fake which button is pressed without an override binding, so you might be stuck with right clicking.

As for displaying tooltips, look at ContainerFrameItemButton_OnEnter and ContainerFrameItemButton_OnLeave.
__________________
  Reply With Quote
08-20-17, 06:57 AM   #11
frohanss
A Cyclonian
AddOn Author - Click to view addons
Join Date: Mar 2011
Posts: 40
Originally Posted by MunkDev View Post
If you haven't already, download the source code and you can look at these things by examining the templates.

The OnClick function (ContainerFrameItemButton_OnClick) uses LeftButton for pickups and any other button for usage. To my knowledge, you can't fake which button is pressed without an override binding, so you might be stuck with right clicking.

As for displaying tooltips, look at ContainerFrameItemButton_OnEnter and ContainerFrameItemButton_OnLeave.
Thanks again
Yes, i think so to. I just add RegisterForClicks("RightButtonUp") to stop left click.
As for the tooltip, i simply can't get it to show more then a second.
I guess this have something todo with the "PreClick"
  Reply With Quote
08-20-17, 08:32 AM   #12
MunkDev
A Scalebane Royal Guard
 
MunkDev's Avatar
AddOn Author - Click to view addons
Join Date: Mar 2015
Posts: 431
You should probably do the ID calculations OnEnter or OnUpdate instead if you want to show the tooltip. The tooltip is not going to show up if you're assigning the IDs when you're clicking the button.

Also, it's a good idea to set the IDs to an empty or invalid slot whenever you don't have any AP items, so you don't accidentally click on some other item that occupies a slot that was previously assigned in your script.
__________________
  Reply With Quote
08-20-17, 02:47 PM   #13
frohanss
A Cyclonian
AddOn Author - Click to view addons
Join Date: Mar 2011
Posts: 40
Not trying to show the tooltip for the item, but the text that i have defined. And it shows for a second everytime i move mouse over it.
But, it's working at thats the most important thing
  Reply With Quote
08-20-17, 03:42 PM   #14
MunkDev
A Scalebane Royal Guard
 
MunkDev's Avatar
AddOn Author - Click to view addons
Join Date: Mar 2015
Posts: 431
The item button template has a default OnUpdate script to keep updating the item tooltip every X seconds. You need to remove that script.
__________________
  Reply With Quote

WoWInterface » Developer Discussions » Lua/XML Help » Macro button inside bag, and still can be opened in combat


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