Browse Source

add shopping max restock

dev
Jørgen Lien Sellæg 4 months ago
parent
commit
3fc255bfbe
  1. 79
      TradeSkillMaster/Auction/AuctionControl.lua
  2. 2
      TradeSkillMaster/TradeSkillMaster.toc
  3. 4
      TradeSkillMaster_AuctionDB/TradeSkillMaster_AuctionDB.toc
  4. 2
      TradeSkillMaster_Shopping/Locale/enUS.lua
  5. 21
      TradeSkillMaster_Shopping/TradeSkillMaster_Shopping.lua
  6. 13
      TradeSkillMaster_Shopping/modules/Options.lua
  7. 8
      TradeSkillMaster_Shopping/modules/Util.lua
  8. 51
      TradeSkillMaster_Shopping/sidebar/Groups.lua
  9. 6
      TradeSkillMaster_Shopping/sidebar/Other.lua

79
TradeSkillMaster/Auction/AuctionControl.lua

@ -15,6 +15,7 @@ TSMAPI:RegisterForTracing(private, "TradeSkillMaster.AuctionControl_private")
LibStub("AceEvent-3.0"):Embed(private) LibStub("AceEvent-3.0"):Embed(private)
private.matchList = {} private.matchList = {}
private.currentPage = {} private.currentPage = {}
private.shoppingPurchasedCounts = {}
local function GetNumInBags(baseItemString) local function GetNumInBags(baseItemString)
@ -43,6 +44,57 @@ local function ValidateAuction(index, list)
return count == private.currentAuction.count and buyout == private.currentAuction.buyout and itemString == private.currentAuction.itemString, data return count == private.currentAuction.count and buyout == private.currentAuction.buyout and itemString == private.currentAuction.itemString, data
end end
local function GetShoppingTotalQuantity(itemString)
itemString = TSMAPI:GetBaseItemString(itemString, true) or itemString
local player, alts = TSMAPI:ModuleAPI("ItemTracker", "playertotal", itemString)
if not player then
alts = nil
end
player = player or 0
alts = alts or 0
local guild = TSMAPI:ModuleAPI("ItemTracker", "guildtotal", itemString) or 0
local auctions = TSMAPI:ModuleAPI("ItemTracker", "auctionstotal", itemString) or 0
local bought = private.shoppingPurchasedCounts[itemString] or 0
return player + alts + guild + auctions + bought
end
local function GetOperationMaxPrice(opSettings, itemString)
if not opSettings or opSettings.maxPrice == nil then return end
if type(opSettings.maxPrice) == "number" then
return opSettings.maxPrice
elseif type(opSettings.maxPrice) == "string" then
local func = TSMAPI:ParseCustomPrice(opSettings.maxPrice)
return func and func(itemString) or nil
end
end
local function ShoppingBuyoutAllowed(itemString, count, perItemBuyout)
local operations = TSMAPI:GetItemOperation(itemString, "Shopping")
if not operations or #operations == 0 then return true end
itemString = TSMAPI:GetBaseItemString(itemString, true) or itemString
for _, opName in ipairs(operations) do
TSMAPI:UpdateOperation("Shopping", opName)
local opSettings = TSM.operations["Shopping"] and TSM.operations["Shopping"][opName]
if opSettings then
local maxRestock = tonumber(opSettings.maxRestock) or 0
local totalQty = GetShoppingTotalQuantity(itemString)
if maxRestock > 0 and (totalQty + count) > maxRestock then
-- over restock for this operation
elseif opSettings.evenStacks and count % 5 ~= 0 then
-- not an even stack for this operation
elseif opSettings.showAboveMaxPrice then
return true
else
local opMaxPrice = GetOperationMaxPrice(opSettings, itemString)
if opMaxPrice and perItemBuyout and perItemBuyout > 0 and perItemBuyout <= opMaxPrice then
return true
end
end
end
end
return false
end
local diffFrame = CreateFrame("Frame") local diffFrame = CreateFrame("Frame")
diffFrame:Hide() diffFrame:Hide()
diffFrame.num = 0 diffFrame.num = 0
@ -146,6 +198,15 @@ end
function private:DoBuyout() function private:DoBuyout()
if private.isSearching or not private.currentAuction or not private.confirmationFrame:IsVisible() then return end if private.isSearching or not private.currentAuction or not private.confirmationFrame:IsVisible() then return end
local perItemBuyout = private.currentAuction.buyout and private.currentAuction.count and (private.currentAuction.buyout / private.currentAuction.count)
if TSM.groupBuyoutCheck and (not perItemBuyout or not TSM.groupBuyoutCheck(private.currentAuction.itemString, private.currentAuction.count, perItemBuyout)) then
TSM:Print("Max restock quantity reached for this item.")
return
end
if private.module == "Shopping" and not ShoppingBuyoutAllowed(private.currentAuction.itemString, private.currentAuction.count, perItemBuyout) then
TSM:Print("Max restock quantity reached for this item.")
return
end
for i=#private.matchList, 1, -1 do for i=#private.matchList, 1, -1 do
local aucIndex = private.matchList[i] local aucIndex = private.matchList[i]
@ -275,6 +336,10 @@ function private:AUCTION_ITEM_LIST_UPDATE()
TSMAPI.AuctionScan:CacheRemove(prevAuction.itemString, private.currentCacheIndex) TSMAPI.AuctionScan:CacheRemove(prevAuction.itemString, private.currentCacheIndex)
private.currentCacheIndex = nil private.currentCacheIndex = nil
end end
if private.module == "Shopping" and prevAuction.itemString and prevAuction.count then
local baseItemString = TSMAPI:GetBaseItemString(prevAuction.itemString, true)
private.shoppingPurchasedCounts[baseItemString] = (private.shoppingPurchasedCounts[baseItemString] or 0) + prevAuction.count
end
TSM:AuctionControlCallback("OnBuyout", prevAuction) TSM:AuctionControlCallback("OnBuyout", prevAuction)
TSMAPI:FireEvent("TSM:AUCTIONCONTROL:ITEMBOUGHT", prevAuction) TSMAPI:FireEvent("TSM:AUCTIONCONTROL:ITEMBOUGHT", prevAuction)
@ -312,6 +377,9 @@ function TSMAPI.AuctionControl:ShowControlButtons(parent, rt, callback, module,
private.rt = rt private.rt = rt
private.callback = callback private.callback = callback
private.module = module private.module = module
if module == "Shopping" then
wipe(private.shoppingPurchasedCounts)
end
private.postBidPercent = postBidPercent private.postBidPercent = postBidPercent
private.postUndercut = postUndercut private.postUndercut = postUndercut
return private.controlButtons return private.controlButtons
@ -348,6 +416,17 @@ function private:ShowConfirmationWindow()
end end
private:SetCurrentAuction(private.rt:GetSelectedAuction()) private:SetCurrentAuction(private.rt:GetSelectedAuction())
if not private.currentAuction then return end if not private.currentAuction then return end
if private.confirmationMode == "Buyout" then
local perItemBuyout = private.currentAuction.buyout and private.currentAuction.count and (private.currentAuction.buyout / private.currentAuction.count)
if TSM.groupBuyoutCheck and (not perItemBuyout or not TSM.groupBuyoutCheck(private.currentAuction.itemString, private.currentAuction.count, perItemBuyout)) then
TSM:Print("Max restock quantity reached for this item.")
return
end
if private.module == "Shopping" and not ShoppingBuyoutAllowed(private.currentAuction.itemString, private.currentAuction.count, perItemBuyout) then
TSM:Print("Max restock quantity reached for this item.")
return
end
end
private:RegisterEvent("AUCTION_ITEM_LIST_UPDATE") private:RegisterEvent("AUCTION_ITEM_LIST_UPDATE")
diffFrame.num = 0 diffFrame.num = 0

2
TradeSkillMaster/TradeSkillMaster.toc

@ -2,7 +2,7 @@
## Title: |cff00fe00TradeSkillMaster: Revived|r ## Title: |cff00fe00TradeSkillMaster: Revived|r
## Notes: Core addon for the TradeSkillMaster suite, revived for Wrath of the Lich King. Does nothing without modules installed. ## Notes: Core addon for the TradeSkillMaster suite, revived for Wrath of the Lich King. Does nothing without modules installed.
## Author: Sapu94, Bart39, Gnomezilla [Warmane-Icecrown(A)], BlueAo [Warmane], andrew6180, Yoshiyuka, DimaSheiko, and other contributors... ## Author: Sapu94, Bart39, Gnomezilla [Warmane-Icecrown(A)], BlueAo [Warmane], andrew6180, Yoshiyuka, DimaSheiko, and other contributors...
## Version: 2.3.33 ## Version: 2.3.34
## SavedVariables: TradeSkillMasterAppDB, AscensionTSMDB ## SavedVariables: TradeSkillMasterAppDB, AscensionTSMDB
## OptionalDeps: AccurateTime, Ace3, LibDataBroker-1.1, LibDBIcon-1.0, LibExtraTip, TipHelper, LibParse, LibCompress, LibGraph-2.0, SharedMedia, TheUndermineJournal, TheUndermineJournalGE ## OptionalDeps: AccurateTime, Ace3, LibDataBroker-1.1, LibDBIcon-1.0, LibExtraTip, TipHelper, LibParse, LibCompress, LibGraph-2.0, SharedMedia, TheUndermineJournal, TheUndermineJournalGE
## X-Embeds: AccurateTime, Ace3, LibDataBroker-1.1, LibDBIcon-1.0, LibExtraTip, TipHelper, LibParse, LibCompress, LibGraph-2.0 ## X-Embeds: AccurateTime, Ace3, LibDataBroker-1.1, LibDBIcon-1.0, LibExtraTip, TipHelper, LibParse, LibCompress, LibGraph-2.0

4
TradeSkillMaster_AuctionDB/TradeSkillMaster_AuctionDB.toc

@ -2,10 +2,10 @@
## Title: |cff00ff00TradeSkillMaster_AuctionDB|r ## Title: |cff00ff00TradeSkillMaster_AuctionDB|r
## Notes: Stores auction house data and calculates market prices. ## Notes: Stores auction house data and calculates market prices.
## Author: Sapu94, Bart39 ## Author: Sapu94, Bart39
## Version: 2.3.33 ## Version: 2.3.34
## SavedVariables: AscensionTSM_AuctionDB ## SavedVariables: AscensionTSM_AuctionDB
## Dependency: TradeSkillMaster ## Dependency: TradeSkillMaster
## X-Curse-Packaged-Version: 2.3.33 ## X-Curse-Packaged-Version: 2.3.34
## X-Curse-Project-Name: TradeSkillMaster_AuctionDB ## X-Curse-Project-Name: TradeSkillMaster_AuctionDB
## X-Curse-Project-ID: tradeskillmaster_auctiondb ## X-Curse-Project-ID: tradeskillmaster_auctiondb
## X-Curse-Repository-ID: wow/tradeskillmaster_auctiondb/mainline ## X-Curse-Repository-ID: wow/tradeskillmaster_auctiondb/mainline

2
TradeSkillMaster_Shopping/Locale/enUS.lua

@ -81,6 +81,8 @@ L["Max Disenchant Level"] = true
L["Max Disenchant Search Percent"] = true L["Max Disenchant Search Percent"] = true
L["Max Shopping Price:"] = true L["Max Shopping Price:"] = true
L["Maximum Auction Price (per item)"] = true L["Maximum Auction Price (per item)"] = true
L["Max Restock Quantity"] = true
L["If set above 0, Shopping will only buy up to this total quantity for items in groups using this operation."] = true
L["Maximum Quantity to Buy:"] = true L["Maximum Quantity to Buy:"] = true
L["Maximum quantity purchased for %s."] = true L["Maximum quantity purchased for %s."] = true
L["Maximum quantity purchased for destroy search."] = true L["Maximum quantity purchased for destroy search."] = true

21
TradeSkillMaster_Shopping/TradeSkillMaster_Shopping.lua

@ -68,6 +68,7 @@ end
TSM.operationDefaults = { TSM.operationDefaults = {
maxPrice = 1, maxPrice = 1,
maxRestock = 0,
evenStacks = nil, evenStacks = nil,
showAboveMaxPrice = nil, showAboveMaxPrice = nil,
ignorePlayer = {}, ignorePlayer = {},
@ -125,6 +126,19 @@ function TSM:GetMaxPrice(operationPrice, itemString)
return price ~= 0 and price or nil, err return price ~= 0 and price or nil, err
end end
function TSM:GetTotalQuantity(itemString)
itemString = TSMAPI:GetBaseItemString(itemString, true) or itemString
local player, alts = TSMAPI:ModuleAPI("ItemTracker", "playertotal", itemString)
if not player then
alts = nil
end
player = player or 0
alts = alts or 0
local guild = TSMAPI:ModuleAPI("ItemTracker", "guildtotal", itemString) or 0
local auctions = TSMAPI:ModuleAPI("ItemTracker", "auctionstotal", itemString) or 0
return player + alts + guild + auctions
end
function TSM:AddSidebarFeature(...) function TSM:AddSidebarFeature(...)
TSM.modules.Sidebar:AddSidebarFeature(...) TSM.modules.Sidebar:AddSidebarFeature(...)
end end
@ -137,9 +151,16 @@ function TSM:GetTooltip(itemString)
local operations = TSMAPI:GetItemOperation(itemString, "Shopping") local operations = TSMAPI:GetItemOperation(itemString, "Shopping")
if not operations then return end if not operations then return end
local maxPrice local maxPrice
local totalQty = TSM:GetTotalQuantity(itemString) or 0
for _, operationName in ipairs(operations) do for _, operationName in ipairs(operations) do
TSMAPI:UpdateOperation("Shopping", operationName) TSMAPI:UpdateOperation("Shopping", operationName)
local operation = TSM.operations[operationName] local operation = TSM.operations[operationName]
if operation then
local maxRestock = tonumber(operation.maxRestock) or 0
if maxRestock > 0 and totalQty >= maxRestock then
operation = nil
end
end
if operation then if operation then
local price = TSM:GetMaxPrice(operation.maxPrice, itemString) local price = TSM:GetMaxPrice(operation.maxPrice, itemString)
if price then if price then

13
TradeSkillMaster_Shopping/modules/Options.lua

@ -305,6 +305,18 @@ function Options:DrawOperationGeneral(container, operationName)
disabled = operation.relationships.maxprice, disabled = operation.relationships.maxprice,
tooltip = L["The highest price per item you will pay for items in affected by this operation."], tooltip = L["The highest price per item you will pay for items in affected by this operation."],
}, },
{
type = "Slider",
settingInfo = { operation, "maxRestock" },
label = L["Max Restock Quantity"],
disabled = operation.relationships.maxRestock,
isPercent = false,
min = 0,
max = 5000,
step = 1,
relativeWidth = 0.49,
tooltip = L["If set above 0, Shopping will only buy up to this total quantity for items in groups using this operation."],
},
{ {
type = "CheckBox", type = "CheckBox",
label = L["Show Auctions Above Max Price"], label = L["Show Auctions Above Max Price"],
@ -333,6 +345,7 @@ function Options:DrawOperationRelationships(container, operationName)
{ {
label = L["General Settings"], label = L["General Settings"],
{ key = "maxPrice", label = L["Maximum Auction Price (per item)"] }, { key = "maxPrice", label = L["Maximum Auction Price (per item)"] },
{ key = "maxRestock", label = L["Max Restock Quantity"] },
{ key = "showAboveMaxPrice", label = L["Show Auctions Above Max Price"] }, { key = "showAboveMaxPrice", label = L["Show Auctions Above Max Price"] },
{ key = "evenStacks", label = L["Even (5/10/15/20) Stacks Only"] }, { key = "evenStacks", label = L["Even (5/10/15/20) Stacks Only"] },
}, },

8
TradeSkillMaster_Shopping/modules/Util.lua

@ -91,6 +91,12 @@ function private:CreateSearchFrame()
private.controlButtons.cancel:Disable() private.controlButtons.cancel:Disable()
private.controlButtons.post:Disable() private.controlButtons.post:Disable()
end end
if private.controlButtons.buyout:IsEnabled() and TSM.groupBuyoutCheck then
local perItemBuyout = data.auctionRecord.GetItemBuyout and data.auctionRecord:GetItemBuyout() or data.auctionRecord.buyout
if not TSM.groupBuyoutCheck(data.itemString, data.auctionRecord.count, perItemBuyout) then
private.controlButtons.buyout:Disable()
end
end
if private:HasInBags(TSMAPI:GetBaseItemString(data.itemString)) then if private:HasInBags(TSMAPI:GetBaseItemString(data.itemString)) then
private.controlButtons.post:Enable() private.controlButtons.post:Enable()
end end
@ -143,6 +149,8 @@ function Util:HideSearchFrame(forceStop)
TSMAPI.AuctionControl:HideControlButtons() TSMAPI.AuctionControl:HideControlButtons()
TSMAPI.AuctionScan:StopScan(forceStop ~= false) TSMAPI.AuctionScan:StopScan(forceStop ~= false)
TSMAPI.AuctionScan:ClearCache() TSMAPI.AuctionScan:ClearCache()
TSM.searchCallback = nil
TSM.groupBuyoutCheck = nil
end end

51
TradeSkillMaster_Shopping/sidebar/Groups.lua

@ -1,18 +1,23 @@
local TSM = select(2, ...) local TSM = select(2, ...)
local L = LibStub("AceLocale-3.0"):GetLocale("TradeSkillMaster_Shopping") -- loads the localization table local L = LibStub("AceLocale-3.0"):GetLocale("TradeSkillMaster_Shopping") -- loads the localization table
local private = {itemOperations={}} local private = {itemOperations={}, purchasedCounts={}}
local function GetActiveOperations(itemString, operations) local function GetActiveOperations(itemString, operations)
if not operations or #operations == 0 then return end if not operations or #operations == 0 then return end
local totalQty = TSM:GetTotalQuantity(itemString) or 0
totalQty = totalQty + (private.purchasedCounts[itemString] or 0)
local active = {} local active = {}
for _, opName in ipairs(operations) do for _, opName in ipairs(operations) do
TSMAPI:UpdateOperation("Shopping", opName) TSMAPI:UpdateOperation("Shopping", opName)
local opSettings = TSM.operations[opName] local opSettings = TSM.operations[opName]
if opSettings then if opSettings then
local maxRestock = tonumber(opSettings.maxRestock) or 0
if maxRestock <= 0 or totalQty < maxRestock then
tinsert(active, opSettings) tinsert(active, opSettings)
end end
end end
end
return active return active
end end
@ -81,8 +86,13 @@ function private.ScanCallback(event, ...)
if not operations or #operations == 0 then return end if not operations or #operations == 0 then return end
auctionItem:FilterRecords(function(record) auctionItem:FilterRecords(function(record)
local buyout = record:GetItemBuyout() or 0 local buyout = record:GetItemBuyout() or 0
local totalQty = TSM:GetTotalQuantity(itemString) or 0
totalQty = totalQty + (private.purchasedCounts[itemString] or 0)
for _, operation in ipairs(operations) do for _, operation in ipairs(operations) do
if operation.evenStacks and record.count % 5 ~= 0 then local maxRestock = tonumber(operation.maxRestock) or 0
if maxRestock > 0 and (totalQty + record.count) > maxRestock then
-- this operation can't accept more of this item
elseif operation.evenStacks and record.count % 5 ~= 0 then
-- not an even stack for this operation -- not an even stack for this operation
elseif operation.showAboveMaxPrice then elseif operation.showAboveMaxPrice then
return false return false
@ -113,6 +123,39 @@ end
function private.StartScan() function private.StartScan()
TSMAPI:FireEvent("SHOPPING:GROUPS:STARTSCAN") TSMAPI:FireEvent("SHOPPING:GROUPS:STARTSCAN")
wipe(private.itemOperations) wipe(private.itemOperations)
wipe(private.purchasedCounts)
TSM.searchCallback = function(event, auction)
if event == "OnBuyout" and auction then
local linkItemString = auction.link and TSMAPI:GetItemString(auction.link)
if linkItemString then
local itemString = TSMAPI:GetBaseItemString(linkItemString, true)
private.purchasedCounts[itemString] = (private.purchasedCounts[itemString] or 0) + (auction.count or 0)
end
end
end
TSM.groupBuyoutCheck = function(itemString, count, buyoutPerItem)
itemString = TSMAPI:GetBaseItemString(itemString, true)
local operations = GetActiveOperations(itemString, private.itemOperations[itemString])
if not operations or #operations == 0 then return false end
for _, operation in ipairs(operations) do
local maxRestock = tonumber(operation.maxRestock) or 0
local totalQty = TSM:GetTotalQuantity(itemString) or 0
totalQty = totalQty + (private.purchasedCounts[itemString] or 0)
if maxRestock > 0 and (totalQty + count) > maxRestock then
-- doesn't fit this operation
elseif operation.evenStacks and count % 5 ~= 0 then
-- not an even stack for this operation
elseif operation.showAboveMaxPrice then
return true
else
local operationPrice = TSM:GetMaxPrice(operation.maxPrice, itemString)
if operationPrice and buyoutPerItem and buyoutPerItem > 0 and buyoutPerItem <= operationPrice then
return true
end
end
end
return false
end
for groupName, data in pairs(private.groupTree:GetSelectedGroupInfo()) do for groupName, data in pairs(private.groupTree:GetSelectedGroupInfo()) do
groupName = TSMAPI:FormatGroupPath(groupName, true) groupName = TSMAPI:FormatGroupPath(groupName, true)
for _, opName in ipairs(data.operations) do for _, opName in ipairs(data.operations) do
@ -129,6 +172,9 @@ function private.StartScan()
if err then if err then
TSM:Printf(L["Invalid custom price source for %s. %s"], TSMAPI:GetSafeItemInfo(itemString) or itemString, err) TSM:Printf(L["Invalid custom price source for %s. %s"], TSMAPI:GetSafeItemInfo(itemString) or itemString, err)
else else
local totalQty = TSM:GetTotalQuantity(itemString) or 0
local maxRestock = tonumber(opSettings.maxRestock) or 0
if maxRestock <= 0 or totalQty < maxRestock then
private.itemOperations[baseItemString] = private.itemOperations[baseItemString] or {} private.itemOperations[baseItemString] = private.itemOperations[baseItemString] or {}
tinsert(private.itemOperations[baseItemString], opName) tinsert(private.itemOperations[baseItemString], opName)
end end
@ -136,6 +182,7 @@ function private.StartScan()
end end
end end
end end
end
local itemList = {} local itemList = {}
for itemString in pairs(private.itemOperations) do for itemString in pairs(private.itemOperations) do

6
TradeSkillMaster_Shopping/sidebar/Other.lua

@ -230,16 +230,22 @@ function private.SniperScanCallback(event, itemString, auctionItem)
vendorPrice = vendor vendorPrice = vendor
end end
local operations = TSMAPI:GetItemOperation(itemString, "Shopping") local operations = TSMAPI:GetItemOperation(itemString, "Shopping")
local totalQty = TSM:GetTotalQuantity(itemString) or 0
for _, opName in ipairs(operations or {}) do for _, opName in ipairs(operations or {}) do
TSMAPI:UpdateOperation("Shopping", opName) TSMAPI:UpdateOperation("Shopping", opName)
local opSettings = TSM.operations[opName] local opSettings = TSM.operations[opName]
if opSettings and opSettings.maxPrice then if opSettings and opSettings.maxPrice then
local maxRestock = tonumber(opSettings.maxRestock) or 0
if maxRestock > 0 and totalQty >= maxRestock then
-- skip this operation if we're already restocked
else
local opPrice = TSM:GetMaxPrice(opSettings.maxPrice, itemString) local opPrice = TSM:GetMaxPrice(opSettings.maxPrice, itemString)
if opPrice then if opPrice then
maxPrice = maxPrice and max(maxPrice, opPrice) or opPrice maxPrice = maxPrice and max(maxPrice, opPrice) or opPrice
end end
end end
end end
end
customPrice = TSM:GetMaxPrice(TSM.db.global.sniperCustomPrice, itemString) customPrice = TSM:GetMaxPrice(TSM.db.global.sniperCustomPrice, itemString)
end end
auctionItem:FilterRecords(function(record) auctionItem:FilterRecords(function(record)

Loading…
Cancel
Save