annotate Modules/Events.lua @ 46:5e981c1df761 ticket7

Changed the way items are converted to be weighted by AH value. there are no options yet.
author Asa Ayers <Asa.Ayers@Gmail.com>
date Tue, 20 Jul 2010 00:12:44 -0700
parents 1ff3b83b104c
children 9ff6a3b02332
rev   line source
Asa@3 1 local addonName, addonTable = ...;
Asa@3 2 local addon = _G[addonName]
Asa@3 3
Asa@38 4 function addon:OnEnable()
Asa@3 5 self:RegisterEvent("MAIL_SHOW")
Asa@4 6 self:RegisterEvent("UNIT_SPELLCAST_START")
Asa@24 7 addon:UpdateCurrentInventory()
Asa@3 8 self:WatchBags()
Asa@9 9
Asa@38 10 self:SetEnabled(nil, self.db.profile.addon_enabled)
Asa@38 11 end
Asa@38 12
Asa@38 13 function addon:OnDisable()
Asa@38 14 self:UnwatchBags()
Asa@38 15 self:UnregisterAllEvents()
Asa@38 16 addon:HideAllFrames()
Asa@3 17 end
Asa@3 18
Asa@3 19 function addon:MAIL_SHOW()
Asa@3 20 self:Debug("MAIL_SHOW")
Asa@39 21 self:UnwatchBags()
Asa@24 22 addon:UpdateCurrentInventory()
Asa@3 23 self.lastMailScan = self:ScanMail()
Asa@7 24
Asa@3 25 self:UnregisterEvent("MAIL_SHOW")
Asa@3 26 self:RegisterEvent("MAIL_CLOSED")
Asa@3 27 self:RegisterEvent("MAIL_INBOX_UPDATE")
Asa@39 28
Asa@39 29 self:GenerateBlankOutbox()
Asa@39 30
Asa@39 31 self:RegisterEvent("MAIL_SUCCESS")
Asa@39 32 end
Asa@39 33
Asa@39 34 function addon:GenerateBlankOutbox()
Asa@39 35 self.mailOutbox = {
Asa@39 36 from = UnitName("player"),
Asa@39 37 to = "",
Asa@39 38 subject = "",
Asa@39 39 link = '',
Asa@39 40 count = 0,
Asa@39 41 COD = 0,
Asa@39 42 key = random(10000),
Asa@39 43 sent = 0,
Asa@39 44 }
Asa@39 45
Asa@39 46 if self.db.factionrealm.outbound_cod[self.mailOutbox.key] ~= nil then
Asa@39 47 return self:GenerateBlankOutbox()
Asa@39 48 end
Asa@39 49 end
Asa@39 50
Asa@40 51 local attachedItems = {}
Asa@39 52 local Orig_SendMail = SendMail
Asa@42 53 local skipCODTracking = false
Asa@42 54
Asa@42 55 StaticPopupDialogs["ItemAuditor_Send_COD_without_tracking_number"] = {
Asa@42 56 text = "ItemAuditor cannot track COD mail with multiple item types attached. Do you want to send this mail without tracking?",
Asa@42 57 button1 = "Yes",
Asa@42 58 button2 = "No",
Asa@42 59 OnAccept = function()
Asa@42 60 skipCODTracking = true
Asa@42 61 end,
Asa@42 62 timeout = 0,
Asa@42 63 whileDead = true,
Asa@42 64 hideOnEscape = true,
Asa@42 65 }
Asa@39 66
Asa@39 67 function SendMail(recipient, subject, body, ...)
Asa@39 68 local self = ItemAuditor
Asa@39 69 self:GenerateBlankOutbox()
Asa@39 70
Asa@39 71 self:Debug(format("[To: %s] [Subject: %s]", recipient, subject))
Asa@39 72
Asa@39 73 self.mailOutbox.COD = GetSendMailCOD()
Asa@39 74
Asa@40 75 attachedItems = {}
Asa@40 76 local totalStacks = 0
Asa@39 77 local link
Asa@40 78 for index = 1, ATTACHMENTS_MAX_SEND do
Asa@39 79 local itemName, _, itemCount = GetSendMailItem(index)
Asa@39 80 local newLink = GetSendMailItemLink(index)
Asa@39 81
Asa@40 82 if newLink ~= nil then
Asa@40 83 newLink = self:GetSafeLink(newLink)
Asa@40 84 totalStacks = totalStacks + 1
Asa@40 85 attachedItems[newLink] = (attachedItems[newLink] or {stacks = 0, count = 0})
Asa@40 86 attachedItems[newLink].stacks = attachedItems[newLink].stacks + 1
Asa@40 87 attachedItems[newLink].count = attachedItems[newLink].count + itemCount
Asa@40 88 attachedItems[newLink].price = 0 -- This is a placeholder for below.
Asa@39 89 end
Asa@40 90 end
Asa@40 91 local pricePerStack = GetSendMailPrice() / totalStacks
Asa@40 92 for link, data in pairs(attachedItems) do
Asa@40 93 data.price = pricePerStack * data.stacks
Asa@40 94 end
Asa@40 95
Asa@42 96 if self.mailOutbox.COD > 0 and skipCODTracking then
Asa@42 97
Asa@42 98 elseif self.mailOutbox.COD > 0 then
Asa@40 99 if self:tcount(attachedItems) > 1 then
Asa@39 100 self:GenerateBlankOutbox()
Asa@42 101 local vararg = ...
Asa@42 102 StaticPopupDialogs["ItemAuditor_Send_COD_without_tracking_number"].OnAccept = function()
Asa@42 103 skipCODTracking = true
Asa@42 104 SendMail(recipient, subject, body, vararg)
Asa@42 105 skipCODTracking = false
Asa@42 106 end
Asa@42 107 StaticPopup_Show ("ItemAuditor_Send_COD_without_tracking_number");
Asa@39 108 return
Asa@39 109 end
Asa@40 110 self:Debug("COD mail")
Asa@39 111
Asa@40 112 subject = format("[IA: %s] %s", self.mailOutbox.key, subject)
Asa@40 113 self.mailOutbox.subject = subject
Asa@40 114 self.mailOutbox.to = recipient
Asa@40 115
Asa@40 116 -- At this point we know there is only one item
Asa@40 117 for link, data in pairs(attachedItems) do
Asa@40 118 self.mailOutbox.link = link
Asa@40 119 self.mailOutbox.count = data.count
Asa@40 120 end
Asa@40 121 else
Asa@40 122 self:Debug("Non-COD mail")
Asa@39 123 end
Asa@40 124
Asa@39 125 return Orig_SendMail(recipient, subject, body, ...)
Asa@39 126 end
Asa@39 127
Asa@39 128 function addon:MAIL_SUCCESS(event)
Asa@42 129 skipCODTracking = false
Asa@40 130 for link, data in pairs(attachedItems) do
Asa@40 131 self:SaveValue(link, data.price, data.count)
Asa@40 132 end
Asa@39 133 if self.mailOutbox.COD > 0 then
Asa@39 134 self:Debug(format("MAIL_SUCCESS %d [To: %s] [Subject: %s] [COD: %s]", self.mailOutbox.key, self.mailOutbox.to, self.mailOutbox.subject, self.mailOutbox.COD))
Asa@39 135
Asa@39 136 self.mailOutbox.sent = time()
Asa@39 137 self.db.factionrealm.outbound_cod[self.mailOutbox.key] = self.mailOutbox
Asa@39 138 end
Asa@39 139
Asa@40 140
Asa@40 141 self:GenerateBlankOutbox()
Asa@3 142 end
Asa@3 143
Asa@3 144 function addon:MAIL_CLOSED()
Asa@23 145 self:Debug("MAIL_CLOSED")
Asa@3 146 addon:UnregisterEvent("MAIL_CLOSED")
Asa@7 147 self:MAIL_INBOX_UPDATE()
Asa@3 148 self:UnregisterEvent("MAIL_INBOX_UPDATE")
Asa@3 149 self:RegisterEvent("MAIL_SHOW")
Asa@39 150 self:WatchBags()
Asa@3 151 end
Asa@3 152
Asa@26 153 local storedCountDiff
Asa@3 154 function addon:MAIL_INBOX_UPDATE()
Asa@23 155 self:Debug("MAIL_INBOX_UPDATE")
Asa@3 156 local newScan = addon:ScanMail()
Asa@3 157 local diff
Asa@39 158
Asa@6 159 for mailType, collection in pairs(self.lastMailScan) do
Asa@7 160 newScan[mailType] = (newScan[mailType] or {})
Asa@26 161 for itemName, data in pairs(collection) do
Asa@26 162 newScan[mailType][itemName] = (newScan[mailType][itemName] or {total=0,count=0})
Asa@26 163 local totalDiff = data.total - newScan[mailType][itemName].total
Asa@26 164 local countDiff = data.count - newScan[mailType][itemName].count
Asa@26 165 --[[
Asa@26 166 In one update the item will be taken and in the following update the invoice
Asa@26 167 will be gone. I need to store the item difference in order ot pass it into
Asa@26 168 SaveValue.
Asa@26 169 ]]
Asa@26 170 if countDiff ~= 0 then
Asa@26 171 storedCountDiff = countDiff
Asa@26 172 end
Asa@26 173
Asa@26 174 if totalDiff ~= 0 then
Asa@39 175 if mailType == "CODPayment" then
Asa@39 176 local trackID
Asa@39 177 trackID, itemName= strsplit("|", itemName, 2)
Asa@39 178 self.db.factionrealm.outbound_cod[tonumber(trackID)] = nil
Asa@39 179 self:Debug("Removing COD Tracker: " .. trackID)
Asa@39 180 end
Asa@26 181 self:SaveValue(itemName, totalDiff, storedCountDiff)
Asa@26 182 storedCountDiff = 0
Asa@6 183 end
Asa@6 184
Asa@3 185 end
Asa@3 186 end
Asa@3 187
Asa@3 188 self.lastMailScan = newScan
Asa@3 189 end
Asa@3 190
Asa@4 191 function addon:UNIT_SPELLCAST_START(event, target, spell)
Asa@5 192 if target == "player" and spell == "Milling" or spell == "Prospecting" or spell == "Disenchanting" then
Asa@23 193 self:Debug(event .. " " .. spell)
Asa@4 194 self:UnwatchBags()
Asa@4 195 self:UpdateCurrentInventory()
Asa@4 196 self:RegisterEvent("UNIT_SPELLCAST_INTERRUPTED")
Asa@4 197 self:RegisterEvent("LOOT_CLOSED")
Asa@3 198 end
Asa@3 199 end
Asa@3 200
Asa@4 201 --[[
Asa@4 202 The item should be destroyed before this point, so the last inventory check
Asa@4 203 needs to be kept so it can be combined with the up coming loot.
Asa@4 204 ]]
Asa@4 205 function addon:LOOT_CLOSED()
Asa@23 206 self:Debug("LOOT_CLOSED")
Asa@4 207 self:UnregisterEvent("LOOT_CLOSED")
Asa@4 208 self:UnregisterEvent("UNIT_SPELLCAST_INTERRUPTED")
Asa@4 209 local inventory = self.lastInventory
Asa@4 210 self:WatchBags()
Asa@4 211 self.lastInventory = inventory
Asa@4 212 end
Asa@3 213
Asa@4 214 function addon:UNIT_SPELLCAST_INTERRUPTED(event, target, spell)
Asa@5 215 if target == "player" and spell == "Milling" or spell == "Prospecting" or spell == "Disenchanting" then
Asa@23 216 self:Debug(event .. " " .. spell)
Asa@4 217 self:UnregisterEvent("UNIT_SPELLCAST_INTERRUPTED")
Asa@4 218 self:UnregisterEvent("LOOT_CLOSED")
Asa@4 219 self:WatchBags()
Asa@4 220 end
Asa@4 221 end
Asa@4 222
Asa@4 223 function addon:UpdateCurrentInventory()
Asa@4 224 self.lastInventory = self:GetCurrentInventory()
Asa@3 225 end
Asa@3 226
Asa@46 227 local function distributeValueByAHValue(self, totalValue, targetItems)
Asa@46 228
Asa@46 229 local weights = {}
Asa@46 230 local totalWeight = 0
Asa@46 231 for link, change in pairs(targetItems) do
Asa@46 232 --[[
Asa@46 233 If something has never been seen on the AH, it must not be very valuable.
Asa@46 234 I'm using 1c so it doesn't have much weight and I can't get a devided by zero error.
Asa@46 235 The only time I know that this is a problem is when crafting a BOP item, and it
Asa@46 236 is always crafted 1 at a time, so a weight of 1 will work.
Asa@46 237 ]]
Asa@46 238 local ap = (addon:GetAuctionPrice(link) or 1)
Asa@46 239 totalWeight = totalWeight + ap
Asa@46 240 weights[link] = ap
Asa@46 241 end
Asa@46 242
Asa@46 243 local valuePerPoint = totalValue / totalWeight
Asa@46 244
Asa@46 245 for link, change in pairs(targetItems) do
Asa@46 246 self:SaveValue(link, weights[link] * valuePerPoint, change)
Asa@46 247 end
Asa@46 248 end
Asa@46 249
Asa@46 250 local function distributeValue(self, totalValue, targetItems)
Asa@46 251 if true then
Asa@46 252 return distributeValueByAHValue(self, totalValue, targetItems)
Asa@46 253 else
Asa@46 254 local valuePerItem = totalChange / positiveCount
Asa@46 255
Asa@46 256 for link, change in pairs(targetItems) do
Asa@46 257 self:SaveValue(link, valuePerItem * change, change)
Asa@46 258 end
Asa@46 259 end
Asa@46 260 end
Asa@46 261
Asa@3 262 function addon:UpdateAudit()
Asa@23 263 -- self:Debug("UpdateAudit " .. event)
Asa@3 264 local currentInventory = self:GetCurrentInventory()
Asa@3 265 local diff = addon:GetInventoryDiff(self.lastInventory, currentInventory)
Asa@3 266
Asa@5 267 local positive, negative = {}, {}
Asa@5 268 local positiveCount, negativeCount = 0, 0
Asa@5 269 for item, count in pairs(diff.items) do
Asa@5 270 if count > 0 then
Asa@5 271 positive[item] = count
Asa@5 272 positiveCount = positiveCount + count
Asa@5 273 elseif count < 0 then
Asa@5 274 negative[item] = count
Asa@5 275 negativeCount = negativeCount + abs(count)
Asa@5 276 end
Asa@5 277 end
Asa@5 278
Asa@23 279 if positiveCount + negativeCount == 0 then
Asa@33 280 --[[
Asa@33 281 Nothing needs to be done, but this will prevent mistakenly attributing
Asa@33 282 the cost of flights to the first item you pick up.
Asa@33 283 ]]
Asa@33 284 elseif diff.money > 0 and self:tcount(positive) > 0 and self:tcount(negative) == 0 then
Asa@15 285 self:Debug("loot")
Asa@20 286 elseif abs(diff.money) > 0 and self:tcount(diff.items) == 1 then
Asa@15 287 self:Debug("purchase or sale")
Asa@3 288
Asa@9 289 for link, count in pairs(diff.items) do
Asa@26 290 self:SaveValue(link, 0 - diff.money, count)
Asa@3 291 end
Asa@23 292 elseif self:tcount(diff.items) > 1 and self:tcount(positive) > 0 and self:tcount(negative) > 0 then
Asa@23 293 -- we must have created/converted something
Asa@23 294 self:Debug("conversion")
Asa@3 295
Asa@23 296 local totalChange = 0
Asa@23 297 for link, change in pairs(negative) do
Asa@23 298 local _, itemCost, count = self:GetItemCost(link, change)
Asa@26 299 self:SaveValue(link, itemCost * change, change)
Asa@10 300
Asa@23 301 totalChange = totalChange + (itemCost * abs(change))
Asa@3 302 end
Asa@23 303
Asa@46 304 distributeValue(self, totalChange, positive)
Asa@23 305 else
Asa@23 306 self:Debug("No match in UpdateAudit.")
Asa@3 307 end
Asa@3 308
Asa@3 309 self.lastInventory = currentInventory
Asa@4 310 addon:WatchBags()
Asa@3 311 end