Skip to content

Commit e014022

Browse files
Merge pull request #25 from Wishmaster117/Add-protected-guild-bank-withdrawals-to-bridge-and-addon
Add protected guild bank withdrawals to bridge and addon
2 parents 05b2ee9 + 3ad235c commit e014022

7 files changed

Lines changed: 126 additions & 35 deletions

Core/MultiBotComm.lua

Lines changed: 22 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2399,6 +2399,27 @@ function Comm.HandleAddonMessage(prefix, message, distribution, sender)
23992399
return true
24002400
end
24012401

2402+
if opcode == "GBANK_RIGHTS" then
2403+
local botName, rest = splitOnce(payload or "", "~")
2404+
local token, rest2 = splitOnce(rest or "", "~")
2405+
local canWithdraw, remaining = splitOnce(rest2 or "", "~")
2406+
botName = trim(urlDecodeField(botName))
2407+
canWithdraw = trim(canWithdraw)
2408+
remaining = tonumber(remaining or "0") or 0
2409+
state.connected = true
2410+
state.lastError = nil
2411+
2412+
local active = getActiveGuildBankRequest(botName, token)
2413+
if active then
2414+
active.rights = {
2415+
canWithdraw = canWithdraw == "1" or string.lower(canWithdraw) == "true",
2416+
remaining = remaining,
2417+
}
2418+
end
2419+
2420+
return true
2421+
end
2422+
24022423
if opcode == "GBANK_END" then
24032424
local botName, token = splitOnce(payload or "", "~")
24042425
botName = trim(urlDecodeField(botName))
@@ -2410,7 +2431,7 @@ function Comm.HandleAddonMessage(prefix, message, distribution, sender)
24102431
local key = string.lower(botName)
24112432
state.guildBankItems[key] = active.items or {}
24122433
if MultiBot.OnBridgeGuildBankItems then
2413-
MultiBot.OnBridgeGuildBankItems(botName, state.guildBankItems[key], active.error, token)
2434+
MultiBot.OnBridgeGuildBankItems(botName, state.guildBankItems[key], active.error, token, active.rights)
24142435
end
24152436
end
24162437

README.md

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -101,6 +101,7 @@ GET~OUTFITS
101101
GET~QUESTS
102102
GET~GAMEOBJECTS
103103
RUN~CRAFT_RECIPE
104+
RUN~ITEM_ACTION
104105
RUN~OUTFIT
105106
RUN~RTI
106107
RUN~COMBAT
@@ -175,7 +176,7 @@ The goal is to remove automatic UI-refresh spam.
175176
</tr>
176177
<tr>
177178
<td>Bot bank / guild bank / vendor buy</td>
178-
<td><strong>Bridge-first</strong> bank snapshots, guild bank snapshots, bank deposit/withdraw, guild bank deposit and vendor buy actions</td>
179+
<td><strong>Bridge-first</strong> bank snapshots, guild bank snapshots, bank deposit/withdraw, guild bank deposit/withdraw and vendor buy actions</td>
179180
</tr>
180181
<tr>
181182
<td>Profession recipe frame</td>
@@ -470,7 +471,7 @@ Implemented bridge-first / chatless areas:
470471
- Inventory refresh with icons and item tooltips.
471472
- Spellbook refresh, with profession/crafting spells separated from the combat spellbook path.
472473
- Character Info frame through the bridge with Blizzard-style tabs for class, profession, secondary, weapon and armor skills, reputations and currencies/emblems.
473-
- Bot bank and guild bank snapshots through the bridge, plus bank deposit/withdraw, guild bank deposit and vendor buy item actions.
474+
- Bot bank and guild bank snapshots through the bridge, plus bank deposit/withdraw, guild bank deposit/withdraw and vendor buy item actions.
474475
- Profession recipe frame through the bridge, opened from profession and secondary skill rows.
475476
- Glyph refresh with icons and glyph tooltips.
476477
- Outfits refresh and actions through the bridge.

TODO.md

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -21,8 +21,6 @@
2121
## Informations bot
2222
* Dans les frames métier ajout d'un bouton pour faire le bot acheter les composants manquants pour crafter l'item.
2323
* Infos personnage : onglets style Blizzard pour compétences, réputations et monnaies.
24-
* Ajouter un bouton pour abandonner les quêtes dans la frame de quêtes finies et en cours des bots
25-
* Ajouter un bouton pour retirer des objets de la banque de guilde
2624

2725

2826
## Inventaire Bot étendu
@@ -32,9 +30,6 @@
3230
* Ajout d'une frame pour afficher le contenu de la banque de guilde.
3331

3432
** TODO
35-
* Voire si on tient compte des droits de guilde pour les retraits et dépôts, et si les rangs des bots évoluent dans playerbots.
36-
* Uniformiser le layout des frames de banque bot et BDG
37-
* Ajouter un bouton retrait à la frame BDG
3833
* Afficher les sous de la guilde dans la frame BDG
3934

4035
## Frame Loot
@@ -112,7 +107,8 @@
112107
* Réputations bridge-first dans la frame Infos personnage.
113108
* Monnaies / emblèmes bridge-first dans la frame Infos personnage, avec argent du bot.
114109
* Banque bot bridge-first avec consultation, dépôt et retrait.
115-
* Banque de guilde bot bridge-first avec consultation et dépôt.
110+
* Banque de guilde bot bridge-first avec consultation, dépôt et retrait protégé par les droits de guilde.
111+
* Layout des frames banque bot et BDG uniformisé avec fond interne sombre.
116112
* Achat vendeur bridge-first depuis les composants manquants de recette métier.
117113
* Profession recipes bridge-first.
118114
* Craft de recettes métier via bridge `RUN~CRAFT_RECIPE`.

UI/MultiBotBankFrame.lua

Lines changed: 74 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ local BANK_FRAME_X = -360
1010
local BANK_ROW_WIDTH = 300
1111
local BANK_TEXT_WIDTH = 210
1212
local BANK_WITHDRAW_BUTTON_WIDTH = 70
13+
local BANK_WITHDRAW_BUTTON_OFFSET_X = -8
1314
local BANK_REFRESH_DELAY = 0.65
1415

1516
local function L(key, fallback)
@@ -34,6 +35,29 @@ local function setButtonEnabled(button, enabled)
3435
end
3536
end
3637

38+
local function addSimpleBackdrop(frame, bgAlpha)
39+
if not frame or not frame.SetBackdrop then
40+
return
41+
end
42+
43+
frame:SetBackdrop({
44+
bgFile = "Interface\\Buttons\\WHITE8x8",
45+
edgeFile = "Interface\\Tooltips\\UI-Tooltip-Border",
46+
tile = true,
47+
tileSize = 16,
48+
edgeSize = 14,
49+
insets = { left = 3, right = 3, top = 3, bottom = 3 },
50+
})
51+
52+
if frame.SetBackdropColor then
53+
frame:SetBackdropColor(0.06, 0.06, 0.08, bgAlpha or 0.90)
54+
end
55+
56+
if frame.SetBackdropBorderColor then
57+
frame:SetBackdropBorderColor(0.35, 0.35, 0.35, 0.95)
58+
end
59+
end
60+
3761
local function createWindow(name, title, width, height, pointX)
3862
if AceGUI then
3963
local widget = AceGUI:Create("Window")
@@ -44,6 +68,11 @@ local function createWindow(name, title, width, height, pointX)
4468
widget.frame:SetPoint("CENTER", UIParent, "CENTER", pointX or 0, 0)
4569
widget.frame:SetFrameStrata("DIALOG")
4670
widget:EnableResize(false)
71+
72+
if widget.content then
73+
addSimpleBackdrop(widget.content, 0.90)
74+
end
75+
4776
return widget
4877
end
4978

@@ -54,9 +83,15 @@ local function createWindow(name, title, width, height, pointX)
5483
frame.title = frame:CreateFontString(nil, "OVERLAY", "GameFontNormal")
5584
frame.title:SetPoint("TOP", 0, -7)
5685
frame.title:SetText(title)
86+
87+
frame.content = CreateFrame("Frame", nil, frame)
88+
frame.content:SetPoint("TOPLEFT", frame, "TOPLEFT", 10, -30)
89+
frame.content:SetPoint("BOTTOMRIGHT", frame, "BOTTOMRIGHT", -10, 10)
90+
addSimpleBackdrop(frame.content, 0.90)
91+
5792
return {
5893
frame = frame,
59-
content = frame,
94+
content = frame.content,
6095
SetTitle = function(self, value) self.frame.title:SetText(value) end,
6196
Show = function(self) self.frame:Show() end,
6297
Hide = function(self) self.frame:Hide() end,
@@ -172,8 +207,24 @@ local function getBankModeBridgeRequiredText(mode)
172207
return L("inventory.bank.bridge.required", "Bank bridge is not connected.")
173208
end
174209

175-
local function canWithdrawFromMode(mode)
176-
return mode ~= "gbank"
210+
local function getWithdrawActionForMode(mode)
211+
if mode == "gbank" then
212+
return "GBANK_WITHDRAW"
213+
end
214+
215+
return "BANK_WITHDRAW"
216+
end
217+
218+
local function canWithdrawFromFrame(frame)
219+
if not frame then
220+
return false
221+
end
222+
223+
if frame.mode == "gbank" then
224+
return frame.gbankCanWithdraw == true
225+
end
226+
227+
return true
177228
end
178229

179230
local function ensureBankFrame()
@@ -209,18 +260,24 @@ local function ensureBankFrame()
209260
row.text:SetHeight(22)
210261

211262
row.withdrawButton = CreateFrame("Button", nil, row, "UIPanelButtonTemplate")
212-
row.withdrawButton:SetPoint("RIGHT", row, "RIGHT", 0, 0)
263+
row.withdrawButton:SetPoint("RIGHT", row, "RIGHT", BANK_WITHDRAW_BUTTON_OFFSET_X, 0)
213264
row.withdrawButton:SetWidth(BANK_WITHDRAW_BUTTON_WIDTH)
214265
row.withdrawButton:SetHeight(20)
215266
row.withdrawButton:SetText(L("inventory.bank.withdraw", "Withdraw"))
216267
row.withdrawButton:SetScript("OnClick", function()
217268
local item = row.item
218-
if not item or not frame.botName or not canWithdrawFromMode(frame.mode) then
269+
local action = getWithdrawActionForMode(frame.mode)
270+
if not item or not frame.botName or not action then
271+
return
272+
end
273+
274+
if not canWithdrawFromFrame(frame) then
275+
frame.status:SetText(getBankReasonText("NO_GUILD_BANK_RIGHTS"))
219276
return
220277
end
221278

222279
if MultiBot.Comm and MultiBot.Comm.RunInventoryItemAction then
223-
local token = MultiBot.Comm.RunInventoryItemAction(frame.botName, "BANK_WITHDRAW", item.itemId, 0)
280+
local token = MultiBot.Comm.RunInventoryItemAction(frame.botName, action, item.itemId, 0)
224281
if token then
225282
frame.status:SetText(L("inventory.bank.withdraw.pending", "Withdraw requested..."))
226283
setButtonEnabled(row.withdrawButton, false)
@@ -279,9 +336,9 @@ local function ensureBankFrame()
279336
if item then
280337
row.icon:SetTexture(MultiBot.SafeTexturePath(item.icon))
281338
row.text:SetText((item.name or ("item:" .. item.itemId)) .. " |cff999999x" .. tostring(item.count or 1) .. "|r")
282-
if canWithdrawFromMode(self.mode) then
339+
if getWithdrawActionForMode(self.mode) then
283340
row.withdrawButton:SetText(L("inventory.bank.withdraw", "Withdraw"))
284-
setButtonEnabled(row.withdrawButton, true)
341+
setButtonEnabled(row.withdrawButton, canWithdrawFromFrame(self))
285342
row.withdrawButton:Show()
286343
else
287344
row.withdrawButton:Hide()
@@ -304,9 +361,11 @@ local function ensureBankFrame()
304361
frame:render()
305362
end)
306363

307-
frame.setItems = function(self, botName, lines, errorReason, mode)
364+
frame.setItems = function(self, botName, lines, errorReason, mode, guildBankRights)
308365
self.botName = botName
309366
self.mode = mode or self.mode or "bank"
367+
self.gbankCanWithdraw = self.mode == "gbank" and type(guildBankRights) == "table" and guildBankRights.canWithdraw == true
368+
self.gbankWithdrawRemaining = self.mode == "gbank" and type(guildBankRights) == "table" and tonumber(guildBankRights.remaining or 0) or 0
310369
self.items = {}
311370
self.page = 1
312371
setWindowTitle(self, getBankModeTitle(self.mode) .. " - " .. tostring(botName or ""))
@@ -341,6 +400,8 @@ function MultiBot.OpenBotBank(botName)
341400
local frame = ensureBankFrame()
342401
frame.botName = botName
343402
frame.mode = "bank"
403+
frame.gbankCanWithdraw = false
404+
frame.gbankWithdrawRemaining = 0
344405
frame.items = {}
345406
frame.page = 1
346407
setWindowTitle(frame, getBankModeTitle(frame.mode) .. " - " .. botName)
@@ -365,6 +426,8 @@ function MultiBot.OpenBotGuildBank(botName)
365426
local frame = ensureBankFrame()
366427
frame.botName = botName
367428
frame.mode = "gbank"
429+
frame.gbankCanWithdraw = false
430+
frame.gbankWithdrawRemaining = 0
368431
frame.items = {}
369432
frame.page = 1
370433
setWindowTitle(frame, getBankModeTitle(frame.mode) .. " - " .. botName)
@@ -428,8 +491,8 @@ function MultiBot.OnBridgeBankItems(botName, lines, errorReason)
428491
ensureBankFrame():setItems(botName, lines or {}, errorReason, "bank")
429492
end
430493

431-
function MultiBot.OnBridgeGuildBankItems(botName, lines, errorReason)
432-
ensureBankFrame():setItems(botName, lines or {}, errorReason, "gbank")
494+
function MultiBot.OnBridgeGuildBankItems(botName, lines, errorReason, token, guildBankRights)
495+
ensureBankFrame():setItems(botName, lines or {}, errorReason, "gbank", guildBankRights)
433496
end
434497

435498
function MultiBot.InitializeBankFrame()

UI/MultiBotInventoryItem.lua

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -548,7 +548,7 @@ function MultiBot.OnBridgeInventoryItemActionResult(botName, action, itemId, res
548548
if MultiBot.RefreshBotBank and (action == "BANK_DEPOSIT" or action == "BANK_WITHDRAW") then
549549
MultiBot.RefreshBotBank(botName, 0.65)
550550
end
551-
if action == "GBANK_DEPOSIT" and MultiBot.RefreshBotGuildBank then
551+
if (action == "GBANK_DEPOSIT" or action == "GBANK_WITHDRAW") and MultiBot.RefreshBotGuildBank then
552552
MultiBot.RefreshBotGuildBank(botName, 0.65)
553553
end
554554
if action == "BUY_ITEM" and MultiBot.professionRecipeFrame and MultiBot.professionRecipeFrame:IsShown()
@@ -573,6 +573,17 @@ function MultiBot.OnBridgeInventoryItemActionResult(botName, action, itemId, res
573573
end
574574

575575
local reasonText = getInventoryItemActionReason(reason)
576+
if (action == "BANK_WITHDRAW" or action == "GBANK_WITHDRAW")
577+
and MultiBot.bankFrame and MultiBot.bankFrame.IsShown and MultiBot.bankFrame:IsShown()
578+
and MultiBot.bankFrame.botName == botName then
579+
if MultiBot.bankFrame.status then
580+
MultiBot.bankFrame.status:SetText(reasonText ~= "" and reasonText or tostring(reason or ""))
581+
end
582+
if MultiBot.bankFrame.render then
583+
MultiBot.bankFrame:render()
584+
end
585+
end
586+
576587
if action == "BUY_ITEM" and MultiBot.professionRecipeFrame and MultiBot.professionRecipeFrame:IsShown()
577588
and MultiBot.professionRecipeFrame.botName == botName
578589
and MultiBot.professionRecipeFrame.status then

docs/multibot_bridge_chatless_roadmap.md

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -146,9 +146,9 @@ Le but n’est pas de supprimer ces commandes. Le but est de ne plus les lancer
146146
- [x] Endpoint côté bridge : `GET~BANK~<bot>~<token>`
147147
- [x] Réponses en paquets courts : `BANK_BEGIN`, `BANK_ITEM`, `BANK_ERROR`, `BANK_END`
148148
- [x] Endpoint côté bridge : `GET~GBANK~<bot>~<token>`
149-
- [x] Réponses en paquets courts : `GBANK_BEGIN`, `GBANK_ITEM`, `GBANK_ERROR`, `GBANK_END`
149+
- [x] Réponses en paquets courts : `GBANK_BEGIN`, `GBANK_RIGHTS`, `GBANK_ITEM`, `GBANK_ERROR`, `GBANK_END`
150150
- [x] Endpoint côté bridge : `RUN~ITEM_ACTION~<bot>~<token>~<action>~<itemId>~<count>`
151-
- [x] Actions validées : dépôt banque bot, retrait banque bot, dépôt banque de guilde et achat vendeur
151+
- [x] Actions validées : dépôt banque bot, retrait banque bot, dépôt banque de guilde, retrait banque de guilde et achat vendeur
152152
- [x] Consultation BDG basée sur la guilde du bot, sans exiger que le joueur soit dans la même guilde
153153
- [x] Détection des banquiers neutres avec flags compatibles Dalaran
154154
- [x] Messages d'erreur structurés pour banquier introuvable, droits BDG, vendeur introuvable, objet non vendu et monnaie spéciale
@@ -283,7 +283,7 @@ Avec beaucoup de bots, éviter les réponses globales trop grosses.
283283
- `GET~BOT_EMBLEMS` répond en paquets `BOT_EMBLEMS_BEGIN` / `BOT_EMBLEM_ITEM` / `BOT_EMBLEMS_MONEY` / `BOT_EMBLEMS_END` ;
284284
- `GET~PROFESSION_RECIPES` répond en paquets `PROFESSION_RECIPES_BEGIN` / `PROFESSION_RECIPES_ITEM` / `PROFESSION_RECIPES_END` ;
285285
- `GET~BANK` répond en paquets `BANK_BEGIN` / `BANK_ITEM` / `BANK_ERROR` / `BANK_END` ;
286-
- `GET~GBANK` répond en paquets `GBANK_BEGIN` / `GBANK_ITEM` / `GBANK_ERROR` / `GBANK_END` ;
286+
- `GET~GBANK` répond en paquets `GBANK_BEGIN` / `GBANK_RIGHTS` / `GBANK_ITEM` / `GBANK_ERROR` / `GBANK_END` ;
287287
- un paquet global vide peut seulement servir de réponse vide si aucun bot n’est disponible.
288288

289289
---
@@ -330,7 +330,7 @@ Le craft de recette passe par `RUN~CRAFT_RECIPE`. Les recettes à résultat alé
330330

331331
Les extensions inventaire banque, banque de guilde et achat vendeur sont maintenant bridge-first pour les chemins validés. La banque du bot et la banque de guilde du bot peuvent être consultées via `GET~BANK` et `GET~GBANK`.
332332

333-
Les actions dépôt banque, retrait banque, dépôt banque de guilde et achat vendeur passent par `RUN~ITEM_ACTION`. Le retrait banque de guilde reste à traiter séparément si l'UI doit l'exposer plus tard, car il demande des garde-fous supplémentaires côté droits et logs.
333+
Les actions dépôt banque, retrait banque, dépôt banque de guilde, retrait banque de guilde et achat vendeur passent par `RUN~ITEM_ACTION`. Le retrait BDG est exposé dans l'UI avec un bouton grisé quand le bot n'a plus de droits de retrait disponibles.
334334

335335
### Audit chatless final
336336

@@ -435,7 +435,7 @@ Le prochain pas logique est maintenant : **audit résiduel + Roll / ventes / ope
435435
5. tester un craft cuisine sans feu puis avec feu, et vérifier l'erreur localisée ;
436436
6. vérifier en console qu’il n’y a plus de refresh automatique legacy `stats`, `items`, `spells`, `glyphs`, `talents spec list`, `outfit ?` avec `MultiBot.allowLegacyChatFallback = false` ;
437437
7. vérifier que les commandes manuelles volontaires restent fonctionnelles : `who`, `co ?`, `nc ?`, `ss ?`, `.playerbot bot add`, `.playerbot bot remove`, actions inventory, `glyph equip`, sélection de spec et actions Outfits ;
438-
8. poursuivre ensuite avec Roll, ventes existantes, open items bridge-first, retrait BDG et enchantements d'objets si besoin.
438+
8. poursuivre ensuite avec Roll, ventes existantes, open items bridge-first et enchantements d'objets si besoin.
439439

440440
Après cette stabilisation, il restera surtout un audit de nettoyage : supprimer les debug temporaires, garder les fallbacks legacy uniquement quand ils sont utiles au diagnostic, et retirer les parsers historiques devenus morts.
441441

0 commit comments

Comments
 (0)