vanilla-wow-addons – Blame information for rev 1
?pathlinks?
Rev | Author | Line No. | Line |
---|---|---|---|
1 | office | 1 | --[[ |
2 | Informant |
||
3 | An addon for World of Warcraft that shows pertinent information about |
||
4 | an item in a tooltip when you hover over the item in the game. |
||
5 | 3.8.0 (Kangaroo) |
||
6 | $Id: Informant.lua 912 2006-06-26 13:53:44Z mentalpower $ |
||
7 | |||
8 | License: |
||
9 | This program is free software; you can redistribute it and/or |
||
10 | modify it under the terms of the GNU General Public License |
||
11 | as published by the Free Software Foundation; either version 2 |
||
12 | of the License, or (at your option) any later version. |
||
13 | |||
14 | This program is distributed in the hope that it will be useful, |
||
15 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
||
16 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||
17 | GNU General Public License for more details. |
||
18 | |||
19 | You should have received a copy of the GNU General Public License |
||
20 | along with this program(see GLP.txt); if not, write to the Free Software |
||
21 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. |
||
22 | --]] |
||
23 | |||
24 | INFORMANT_VERSION = "3.8.0" |
||
25 | if (INFORMANT_VERSION == "<".."%version%>") then |
||
26 | INFORMANT_VERSION = "3.7.DEV" |
||
27 | end |
||
28 | |||
29 | -- GLOBAL FUNCTION PROTOTYPES: |
||
30 | |||
31 | local getItem--(itemID); itemID is the first value in a blizzard hyperlink id |
||
32 | -- this pattern would extract the id you need: |
||
33 | -- "item:(%d+):%d+:%d+:%d+" |
||
34 | |||
35 | |||
36 | |||
37 | -- LOCAL FUNCTION PROTOTYPES: |
||
38 | local addLine -- addLine(text, color) |
||
39 | local clear -- clear() |
||
40 | local frameActive -- frameActive(isActive) |
||
41 | local frameLoaded -- frameLoaded() |
||
42 | local getCatName -- getCatName(catID) |
||
43 | local getFilter -- getFilter(filter) |
||
44 | local getFilterVal -- getFilterVal(type) |
||
45 | local getItem -- getItem(itemID) |
||
46 | local getRowCount -- getRowCount() |
||
47 | local nilSafeString -- nilSafeString(String) |
||
48 | local onEvent -- onEvent(event) |
||
49 | local onLoad -- onLoad() |
||
50 | local onVariablesLoaded -- onVariablesLoaded() |
||
51 | local onQuit -- onQuit() |
||
52 | local scrollUpdate -- scrollUpdate(offset) |
||
53 | local setDatabase -- setDatabase(database) |
||
54 | local setFilter -- setFilter(key, value) |
||
55 | local setFilterDefaults -- setFilterDefaults() |
||
56 | local setRequirements -- setRequirements(requirements) |
||
57 | local setSkills -- setSkills(skills) |
||
58 | local setVendors -- setVendors(vendors) |
||
59 | local showHideInfo -- showHideInfo() |
||
60 | local skillToName -- skillToName(userSkill) |
||
61 | local split -- split(str, at) |
||
62 | local tooltipHandler -- tooltipHandler(funcVars, retVal, frame, name, link, quality, count, price) |
||
63 | local getKeyBindProfile -- getKeyBindProfile() |
||
64 | local whitespace -- whitespace(length) |
||
65 | |||
66 | -- LOCAL VARIABLES |
||
67 | |||
68 | local self = {} |
||
69 | local lines = {} |
||
70 | local itemInfo = nil |
||
71 | |||
72 | -- GLOBAL VARIABLES |
||
73 | |||
74 | BINDING_HEADER_INFORMANT_HEADER = _INFM('BindingHeader') |
||
75 | BINDING_NAME_INFORMANT_POPUPDOWN = _INFM('BindingTitle') |
||
76 | |||
77 | InformantConfig = {} |
||
78 | |||
79 | -- LOCAL DEFINES |
||
80 | |||
81 | CLASS_TO_CATEGORY_MAP = { |
||
82 | [2] = 1, |
||
83 | [4] = 2, |
||
84 | [1] = 3, |
||
85 | [0] = 4, |
||
86 | [7] = 5, |
||
87 | [6] = 6, |
||
88 | [11] = 7, |
||
89 | [9] = 8, |
||
90 | [5] = 9, |
||
91 | [15] = 10, |
||
92 | } |
||
93 | |||
94 | local filterDefaults = { |
||
95 | ['all'] = 'on', |
||
96 | ['embed'] = 'off', |
||
97 | ['locale'] = 'default', |
||
98 | ['show-vendor'] = 'on', |
||
99 | ['show-vendor-buy'] = 'on', |
||
100 | ['show-vendor-sell'] = 'on', |
||
101 | ['show-usage'] = 'on', |
||
102 | ['show-stack'] = 'on', |
||
103 | ['show-merchant'] = 'on', |
||
104 | ['show-quest'] = 'on', |
||
105 | ['show-icon'] = 'on', |
||
106 | } |
||
107 | |||
108 | -- FUNCTION DEFINITIONS |
||
109 | |||
110 | function split(str, at) |
||
111 | local splut = {} |
||
112 | |||
113 | if (type(str) ~= "string") then return nil end |
||
114 | if (not str) then str = "" end |
||
115 | if (not at) |
||
116 | then table.insert(splut, str) |
||
117 | else |
||
118 | for n, c in string.gfind(str, '([^%'..at..']*)(%'..at..'?)') do |
||
119 | table.insert(splut, n) |
||
120 | if (c == '') then break end |
||
121 | end |
||
122 | end |
||
123 | return splut |
||
124 | end |
||
125 | |||
126 | function skillToName(userSkill) |
||
127 | local skillName = self.skills[tonumber(userSkill)] |
||
128 | local localized = "Unknown" |
||
129 | if (skillName) then |
||
130 | if (_INFM("Skill"..skillName)) then |
||
131 | localized = _INFM("Skill"..skillName) |
||
132 | else |
||
133 | localized = "Unknown:"..skillName |
||
134 | end |
||
135 | end |
||
136 | return localized, skillName |
||
137 | end |
||
138 | |||
139 | function getItem(itemID) |
||
140 | local baseData = self.database[itemID] |
||
141 | if (not baseData) then |
||
142 | return getItemBasic(itemID) |
||
143 | end |
||
144 | |||
145 | local _, _, _, iLevel, sType, _, iCount, _, sTexture = GetItemInfo(itemID) |
||
146 | |||
147 | local baseSplit = split(baseData, ":") |
||
148 | local buy = tonumber(baseSplit[1]) |
||
149 | local sell = tonumber(baseSplit[2]) |
||
150 | local class = tonumber(baseSplit[3]) |
||
151 | local quality = tonumber(baseSplit[4]) |
||
152 | local stack = tonumber(iCount) or tonumber(baseSplit[5]) |
||
153 | local additional = baseSplit[6] |
||
154 | local usedby = baseSplit[7] |
||
155 | local quantity = baseSplit[8] |
||
156 | local limited = baseSplit[9] |
||
157 | local merchantlist = baseSplit[10] |
||
158 | local cat = CLASS_TO_CATEGORY_MAP[class] |
||
159 | |||
160 | local dataItem = { |
||
161 | ['buy'] = buy, |
||
162 | ['sell'] = sell, |
||
163 | ['class'] = class, |
||
164 | ['cat'] = cat, |
||
165 | ['quality'] = quality, |
||
166 | ['stack'] = stack, |
||
167 | ['additional'] = additional, |
||
168 | ['usedby'] = usedby, |
||
169 | ['quantity'] = quantity, |
||
170 | ['limited'] = limited, |
||
171 | ['texture'] = sTexture, |
||
172 | ['fullData'] = true, |
||
173 | } |
||
174 | |||
175 | local addition = "" |
||
176 | if (additional ~= "") then |
||
177 | addition = " - ".._INFM("Addit"..additional) |
||
178 | end |
||
179 | local catName = getCatName(cat) |
||
180 | if (not catName) then |
||
181 | if (sType) then |
||
182 | dataItem.classText = sType..addition |
||
183 | else |
||
184 | dataItem.classText = "Unknown"..addition |
||
185 | end |
||
186 | else |
||
187 | dataItem.classText = catName..addition |
||
188 | end |
||
189 | |||
190 | if (usedby ~= '') then |
||
191 | local usedList = split(usedby, ",") |
||
192 | local skillName, localized, localeString |
||
193 | local usage = "" |
||
194 | dataItem.usedList = {} |
||
195 | if (usedList) then |
||
196 | for pos, userSkill in pairs(usedList) do |
||
197 | localized = skillToName(userSkill) |
||
198 | if (usage == "") then |
||
199 | usage = localized |
||
200 | else |
||
201 | usage = usage .. ", " .. localized |
||
202 | end |
||
203 | table.insert(dataItem.usedList, localized) |
||
204 | end |
||
205 | end |
||
206 | dataItem.usageText = usage |
||
207 | end |
||
208 | |||
209 | local reqSkill = 0 |
||
210 | local reqLevel = 0 |
||
211 | local skillName = "" |
||
212 | |||
213 | local skillsRequired = self.requirements[itemID] |
||
214 | if (skillsRequired) then |
||
215 | local skillSplit = split(skillsRequired, ":") |
||
216 | reqSkill = skillSplit[1] |
||
217 | reqLevel = skillSplit[2] |
||
218 | skillName = skillToName(reqSkill) |
||
219 | end |
||
220 | |||
221 | dataItem.isPlayerMade = (reqSkill ~= 0) |
||
222 | dataItem.reqSkill = reqSkill |
||
223 | dataItem.reqSkillName = skillName |
||
224 | dataItem.reqLevel = iLevel or reqLevel |
||
225 | |||
226 | if (merchantlist ~= '') then |
||
227 | local merchList = split(merchantlist, ",") |
||
228 | local vendName |
||
229 | local vendList = {} |
||
230 | if (merchList) then |
||
231 | for pos, merchID in pairs(merchList) do |
||
232 | vendName = self.vendors[tonumber(merchID)] |
||
233 | if (vendName) then |
||
234 | table.insert(vendList, vendName) |
||
235 | end |
||
236 | end |
||
237 | end |
||
238 | dataItem.vendors = vendList |
||
239 | end |
||
240 | |||
241 | dataItem.quests = {} |
||
242 | dataItem.questCount = 0 |
||
243 | local questItemUse = InformantQuests.usage[itemID] |
||
244 | if (questItemUse) then |
||
245 | local questData = split(questItemUse, ",") |
||
246 | local questInfoSplit, questID, questCount |
||
247 | for pos, questInfo in pairs(questData) do |
||
248 | questInfoSplit = split(questInfo, ":") |
||
249 | questID = tonumber(questInfoSplit[1]) |
||
250 | questCount = tonumber(questInfoSplit[2]) |
||
251 | if (not dataItem.quests[questID]) then |
||
252 | questName = Babylonian.GetString(InformantQuests.names, questID) |
||
253 | dataItem.quests[questID] = { |
||
254 | ['count'] = questCount, |
||
255 | ['name'] = questName, |
||
256 | ['level'] = tonumber(InformantQuests.levels[questID]) |
||
257 | } |
||
258 | dataItem.questCount = dataItem.questCount + 1 |
||
259 | end |
||
260 | end |
||
261 | end |
||
262 | |||
263 | return dataItem |
||
264 | end |
||
265 | |||
266 | function getItemBasic(itemID) |
||
267 | if (not itemID) then return end |
||
268 | local sName, sLink, iQuality, iLevel, sType, sSubType, iCount, sEquipLoc, sTexture = GetItemInfo(tonumber(itemID)) |
||
269 | |||
270 | if (sName) then |
||
271 | local dataItem = { |
||
272 | ['classText'] = sType, |
||
273 | ['quality'] = iQuality, |
||
274 | ['stack'] = iCount, |
||
275 | ['texture'] = sTexture, |
||
276 | ['reqLevel'] = iLevel, |
||
277 | ['fullData'] = false, |
||
278 | } |
||
279 | return dataItem |
||
280 | end |
||
281 | end |
||
282 | |||
283 | function setSkills(skills) |
||
284 | self.skills = skills |
||
285 | Informant.SetSkills = nil -- Set only once |
||
286 | end |
||
287 | |||
288 | function setRequirements(requirements) |
||
289 | self.requirements = requirements |
||
290 | Informant.SetRequirements = nil -- Set only once |
||
291 | end |
||
292 | |||
293 | function setVendors(vendors) |
||
294 | self.vendors = vendors |
||
295 | Informant.SetVendors = nil -- Set only once |
||
296 | end |
||
297 | |||
298 | function setDatabase(database) |
||
299 | self.database = database |
||
300 | Informant.SetDatabase = nil -- Set only once |
||
301 | end |
||
302 | |||
303 | |||
304 | function setFilter(key, value) |
||
305 | if (not InformantConfig.filters) then |
||
306 | InformantConfig.filters = {}; |
||
307 | setFilterDefaults() |
||
308 | end |
||
309 | if (type(value) == "boolean") then |
||
310 | if (value) then |
||
311 | InformantConfig.filters[key] = 'on'; |
||
312 | else |
||
313 | InformantConfig.filters[key] = 'off'; |
||
314 | end |
||
315 | else |
||
316 | InformantConfig.filters[key] = value; |
||
317 | end |
||
318 | end |
||
319 | |||
320 | function getFilterVal(type) |
||
321 | if (not InformantConfig.filters) then |
||
322 | InformantConfig.filters = {} |
||
323 | setFilterDefaults() |
||
324 | end |
||
325 | return InformantConfig.filters[type] |
||
326 | end |
||
327 | |||
328 | function getFilter(filter) |
||
329 | value = getFilterVal(filter) |
||
330 | if ((value == _INFM('CmdOn')) or (value == "on")) then return true |
||
331 | elseif ((value == _INFM('CmdOff')) or (value == "off")) then return false end |
||
332 | return true |
||
333 | end |
||
334 | |||
335 | function getLocale() |
||
336 | local locale = Informant.GetFilterVal('locale'); |
||
337 | if (locale ~= 'on') and (locale ~= 'off') and (locale ~= 'default') then |
||
338 | return locale; |
||
339 | end |
||
340 | return GetLocale(); |
||
341 | end |
||
342 | |||
343 | local categories |
||
344 | function getCatName(catID) |
||
345 | if (not categories) then categories = {GetAuctionItemClasses()} end |
||
346 | for cat, name in categories do |
||
347 | if (cat == catID) then return name end |
||
348 | end |
||
349 | end |
||
350 | |||
351 | function tooltipHandler(funcVars, retVal, frame, name, link, quality, count, price) |
||
352 | -- nothing to do, if informant is disabled |
||
353 | if (not getFilter('all')) then |
||
354 | return; |
||
355 | end; |
||
356 | |||
357 | if EnhTooltip.LinkType(link) ~= "item" then return end |
||
358 | |||
359 | local quant = 0 |
||
360 | local sell = 0 |
||
361 | local buy = 0 |
||
362 | local stacks = 1 |
||
363 | |||
364 | local itemID, randomProp, enchant, uniqID, lame = EnhTooltip.BreakLink(link) |
||
365 | if (itemID and itemID > 0) and (Informant) then |
||
366 | itemInfo = getItem(itemID) |
||
367 | end |
||
368 | if (not itemInfo) then return end |
||
369 | |||
370 | itemInfo.itemName = name |
||
371 | itemInfo.itemLink = link |
||
372 | itemInfo.itemCount = count |
||
373 | itemInfo.itemQuality = quality |
||
374 | |||
375 | stacks = itemInfo.stack |
||
376 | if (not stacks) then stacks = 1 end |
||
377 | |||
378 | buy = tonumber(itemInfo.buy) or 0 |
||
379 | sell = tonumber(itemInfo.sell) or 0 |
||
380 | quant = tonumber(itemInfo.quantity) or 0 |
||
381 | |||
382 | if (quant == 0) and (sell > 0) then |
||
383 | local ratio = buy / sell |
||
384 | if ((ratio > 3) and (ratio < 6)) then |
||
385 | quant = 1 |
||
386 | else |
||
387 | ratio = buy / (sell * 5) |
||
388 | if ((ratio > 3) and (ratio < 6)) then |
||
389 | quant = 5 |
||
390 | end |
||
391 | end |
||
392 | end |
||
393 | if (quant == 0) then quant = 1 end |
||
394 | |||
395 | buy = buy/quant |
||
396 | |||
397 | itemInfo.itemBuy = buy |
||
398 | itemInfo.itemSell = sell |
||
399 | itemInfo.itemQuant = quant |
||
400 | |||
401 | local embedded = getFilter('embed') |
||
402 | |||
403 | if (getFilter('show-icon')) then |
||
404 | if (itemInfo.texture) then |
||
405 | EnhTooltip.SetIcon(itemInfo.texture) |
||
406 | end |
||
407 | end |
||
408 | |||
409 | if (getFilter('show-vendor')) then |
||
410 | if ((buy > 0) or (sell > 0)) then |
||
411 | local bgsc = EnhTooltip.GetTextGSC(buy, true) |
||
412 | local sgsc = EnhTooltip.GetTextGSC(sell, true) |
||
413 | |||
414 | if (count and (count > 1)) then |
||
415 | if (getFilter('show-vendor-buy')) then |
||
416 | EnhTooltip.AddLine(string.format(_INFM('FrmtInfoBuymult'), count, bgsc), buy*count, embedded, true) |
||
417 | EnhTooltip.LineColor(0.8, 0.5, 0.1) |
||
418 | end |
||
419 | if (getFilter('show-vendor-sell')) then |
||
420 | EnhTooltip.AddLine(string.format(_INFM('FrmtInfoSellmult'), count, sgsc), sell*count, embedded, true) |
||
421 | EnhTooltip.LineColor(0.8, 0.5, 0.1) |
||
422 | end |
||
423 | else |
||
424 | if (getFilter('show-vendor-buy')) then |
||
425 | EnhTooltip.AddLine(string.format(_INFM('FrmtInfoBuy')), buy, embedded, true) |
||
426 | EnhTooltip.LineColor(0.8, 0.5, 0.1) |
||
427 | end |
||
428 | if (getFilter('show-vendor-sell')) then |
||
429 | EnhTooltip.AddLine(string.format(_INFM('FrmtInfoSell')), sell, embedded, true) |
||
430 | EnhTooltip.LineColor(0.8, 0.5, 0.1) |
||
431 | end |
||
432 | end |
||
433 | end |
||
434 | end |
||
435 | |||
436 | if (getFilter('show-stack')) then |
||
437 | if (stacks > 1) then |
||
438 | EnhTooltip.AddLine(string.format(_INFM('FrmtInfoStx'), stacks), nil, embedded) |
||
439 | end |
||
440 | end |
||
441 | if (getFilter('show-merchant')) then |
||
442 | if (itemInfo.vendors) then |
||
443 | local merchantCount = table.getn(itemInfo.vendors) |
||
444 | if (merchantCount > 0) then |
||
445 | EnhTooltip.AddLine(string.format(_INFM('FrmtInfoMerchants'), merchantCount), nil, embedded) |
||
446 | EnhTooltip.LineColor(0.5, 0.8, 0.5) |
||
447 | end |
||
448 | end |
||
449 | end |
||
450 | if (getFilter('show-usage')) then |
||
451 | local reagentInfo = "" |
||
452 | if (itemInfo.classText) then |
||
453 | reagentInfo = string.format(_INFM('FrmtInfoClass'), itemInfo.classText) |
||
454 | EnhTooltip.AddLine(reagentInfo, nil, embedded) |
||
455 | EnhTooltip.LineColor(0.6, 0.4, 0.8) |
||
456 | end |
||
457 | if (itemInfo.usedList and itemInfo.usageText) then |
||
458 | if (table.getn(itemInfo.usedList) > 2) then |
||
459 | |||
460 | local currentUseLine = nilSafeString(itemInfo.usedList[1])..", "..nilSafeString(itemInfo.usedList[2]).."," |
||
461 | reagentInfo = string.format(_INFM('FrmtInfoUse'), currentUseLine) |
||
462 | EnhTooltip.AddLine(reagentInfo, nil, embedded) |
||
463 | EnhTooltip.LineColor(0.6, 0.4, 0.8) |
||
464 | |||
465 | for index = 3, table.getn(itemInfo.usedList), 2 do |
||
466 | if (itemInfo.usedList[index+1]) then |
||
467 | reagentInfo = whitespace(string.len(_INFM('FrmtInfoUse')) + 3)..nilSafeString(itemInfo.usedList[index])..", "..nilSafeString(itemInfo.usedList[index+1]).."," |
||
468 | EnhTooltip.AddLine(reagentInfo, nil, embedded) |
||
469 | EnhTooltip.LineColor(0.6, 0.4, 0.8) |
||
470 | else |
||
471 | reagentInfo = whitespace(string.len(_INFM('FrmtInfoUse')) + 3)..nilSafeString(itemInfo.usedList[index]) |
||
472 | EnhTooltip.AddLine(reagentInfo, nil, embedded) |
||
473 | EnhTooltip.LineColor(0.6, 0.4, 0.8) |
||
474 | end |
||
475 | end |
||
476 | else |
||
477 | reagentInfo = string.format(_INFM('FrmtInfoUse'), itemInfo.usageText) |
||
478 | EnhTooltip.AddLine(reagentInfo, nil, embedded) |
||
479 | EnhTooltip.LineColor(0.6, 0.4, 0.8) |
||
480 | end |
||
481 | end |
||
482 | end |
||
483 | if (getFilter('show-quest')) then |
||
484 | if (itemInfo.quests) then |
||
485 | local questCount = itemInfo.questCount |
||
486 | if (questCount > 0) then |
||
487 | EnhTooltip.AddLine(string.format(_INFM('FrmtInfoQuest'), questCount), nil, embedded) |
||
488 | EnhTooltip.LineColor(0.5, 0.5, 0.8) |
||
489 | end |
||
490 | end |
||
491 | end |
||
492 | end |
||
493 | |||
494 | function nilSafeString(str) |
||
495 | if (not str) then str = "" end |
||
496 | return str; |
||
497 | end |
||
498 | |||
499 | function whitespace(length) |
||
500 | local spaces = "" |
||
501 | while length ~= 0 do |
||
502 | spaces = spaces.." " |
||
503 | length = length - 1 |
||
504 | end |
||
505 | return spaces |
||
506 | end |
||
507 | |||
508 | function showHideInfo() |
||
509 | if (InformantFrame:IsVisible()) then |
||
510 | InformantFrame:Hide() |
||
511 | elseif (itemInfo) then |
||
512 | InformantFrameTitle:SetText(_INFM('FrameTitle')) |
||
513 | |||
514 | -- Woohoo! We need to provide any information we can from the item currently in itemInfo |
||
515 | local quality = itemInfo.itemQuality or itemInfo.quality or 0 |
||
516 | |||
517 | local color = "ffffff" |
||
518 | if (quality == 4) then color = "a335ee" |
||
519 | elseif (quality == 3) then color = "0070dd" |
||
520 | elseif (quality == 2) then color = "1eff00" |
||
521 | elseif (quality == 0) then color = "9d9d9d" |
||
522 | end |
||
523 | |||
524 | clear() |
||
525 | addLine(string.format(_INFM('InfoHeader'), color, itemInfo.itemName)) |
||
526 | |||
527 | local buy = itemInfo.itemBuy or itemInfo.buy or 0 |
||
528 | local sell = itemInfo.itemSell or itemInfo.sell or 0 |
||
529 | local quant = itemInfo.itemQuant or itemInfo.quantity or 0 |
||
530 | local count = itemInfo.itemCount or 1 |
||
531 | |||
532 | if ((buy > 0) or (sell > 0)) then |
||
533 | local bgsc = EnhTooltip.GetTextGSC(buy, true) |
||
534 | local sgsc = EnhTooltip.GetTextGSC(sell, true) |
||
535 | |||
536 | if (count and (count > 1)) then |
||
537 | local bqgsc = EnhTooltip.GetTextGSC(buy*count, true) |
||
538 | local sqgsc = EnhTooltip.GetTextGSC(sell*count, true) |
||
539 | addLine(string.format(_INFM('FrmtInfoBuymult'), count, bgsc)..": "..bqgsc, "ee8822") |
||
540 | addLine(string.format(_INFM('FrmtInfoSellmult'), count, sgsc)..": "..sqgsc, "ee8822") |
||
541 | else |
||
542 | addLine(string.format(_INFM('FrmtInfoBuy'))..": "..bgsc, "ee8822") |
||
543 | addLine(string.format(_INFM('FrmtInfoSell'))..": "..sgsc, "ee8822") |
||
544 | end |
||
545 | end |
||
546 | |||
547 | if (itemInfo.stack > 1) then |
||
548 | addLine(string.format(_INFM('FrmtInfoStx'), itemInfo.stack)) |
||
549 | end |
||
550 | |||
551 | local reagentInfo = "" |
||
552 | if (itemInfo.classText) then |
||
553 | reagentInfo = string.format(_INFM('FrmtInfoClass'), itemInfo.classText) |
||
554 | addLine(reagentInfo, "aa66ee") |
||
555 | end |
||
556 | if (itemInfo.usageText) then |
||
557 | reagentInfo = string.format(_INFM('FrmtInfoUse'), itemInfo.usageText) |
||
558 | addLine(reagentInfo, "aa66ee") |
||
559 | end |
||
560 | |||
561 | if (itemInfo.isPlayerMade) then |
||
562 | addLine(string.format(_INFM('InfoPlayerMade'), itemInfo.reqLevel, itemInfo.reqSkillName), "5060ff") |
||
563 | end |
||
564 | |||
565 | if (itemInfo.quests) then |
||
566 | local questCount = itemInfo.questCount |
||
567 | if (questCount > 0) then |
||
568 | addLine("") |
||
569 | addLine(string.format(_INFM('FrmtInfoQuest'), questCount), nil, embed) |
||
570 | addLine(string.format(_INFM('InfoQuestHeader'), questCount), "70ee90") |
||
571 | for pos, quest in itemInfo.quests do |
||
572 | addLine(string.format(_INFM('InfoQuestName'), quest.count, quest.name, quest.level), "80ee80") |
||
573 | end |
||
574 | addLine(string.format((_INFM('InfoQuestSource')).." WoWGuru.com")); |
||
575 | end |
||
576 | end |
||
577 | |||
578 | if (itemInfo.vendors) then |
||
579 | local vendorCount = table.getn(itemInfo.vendors) |
||
580 | if (vendorCount > 0) then |
||
581 | addLine("") |
||
582 | addLine(string.format(_INFM('InfoVendorHeader'), vendorCount), "ddff40") |
||
583 | for pos, merchant in itemInfo.vendors do |
||
584 | addLine(string.format(" ".._INFM('InfoVendorName'), merchant), "eeee40") |
||
585 | end |
||
586 | end |
||
587 | end |
||
588 | InformantFrame:Show() |
||
589 | else |
||
590 | clear() |
||
591 | addLine(_INFM('InfoNoItem'), "ff4010") |
||
592 | InformantFrame:Show() |
||
593 | end |
||
594 | end |
||
595 | |||
596 | function onQuit() |
||
597 | if (not InformantConfig.position) then |
||
598 | InformantConfig.position = { } |
||
599 | end |
||
600 | InformantConfig.position.x, InformantConfig.position.y = InformantFrame:GetCenter() |
||
601 | end |
||
602 | |||
603 | function onLoad() |
||
604 | this:RegisterEvent("ADDON_LOADED") |
||
605 | |||
606 | if (not InformantConfig) then |
||
607 | InformantConfig = {} |
||
608 | setFilterDefaults() |
||
609 | end |
||
610 | |||
611 | InformantFrameTitle:SetText(_INFM('FrameTitle')) |
||
612 | -- Informant.InitTrades(); |
||
613 | end |
||
614 | |||
615 | local function frameLoaded() |
||
616 | Stubby.RegisterEventHook("PLAYER_LEAVING_WORLD", "Informant", onQuit) |
||
617 | Stubby.RegisterFunctionHook("EnhTooltip.AddTooltip", 300, tooltipHandler) |
||
618 | |||
619 | onLoad() |
||
620 | |||
621 | -- Setup the default for stubby to always load (people can override this on a |
||
622 | -- per toon basis) |
||
623 | Stubby.SetConfig("Informant", "LoadType", "always", true) |
||
624 | |||
625 | -- Register our temporary command hook with stubby |
||
626 | Stubby.RegisterBootCode("Informant", "CommandHandler", [[ |
||
627 | local function cmdHandler(msg) |
||
628 | local i,j, cmd, param = string.find(string.lower(msg), "^([^ ]+) (.+)$") |
||
629 | if (not cmd) then cmd = string.lower(msg) end |
||
630 | if (not cmd) then cmd = "" end |
||
631 | if (not param) then param = "" end |
||
632 | if (cmd == "load") then |
||
633 | if (param == "") then |
||
634 | Stubby.Print("Manually loading Informant...") |
||
635 | LoadAddOn("Informant") |
||
636 | elseif (param == "always") then |
||
637 | Stubby.Print("Setting Informant to always load for this character") |
||
638 | Stubby.SetConfig("Informant", "LoadType", param) |
||
639 | LoadAddOn("Informant") |
||
640 | elseif (param == "never") then |
||
641 | Stubby.Print("Setting Informant to never load automatically for this character (you may still load manually)") |
||
642 | Stubby.SetConfig("Informant", "LoadType", param) |
||
643 | else |
||
644 | Stubby.Print("Your command was not understood") |
||
645 | end |
||
646 | else |
||
647 | Stubby.Print("Informant is currently not loaded.") |
||
648 | Stubby.Print(" You may load it now by typing |cffffffff/informant load|r") |
||
649 | Stubby.Print(" You may also set your loading preferences for this character by using the following commands:") |
||
650 | Stubby.Print(" |cffffffff/informant load always|r - Informant will always load for this character") |
||
651 | Stubby.Print(" |cffffffff/informant load never|r - Informant will never load automatically for this character (you may still load it manually)") |
||
652 | end |
||
653 | end |
||
654 | SLASH_INFORMANT1 = "/informant" |
||
655 | SLASH_INFORMANT2 = "/inform" |
||
656 | SLASH_INFORMANT3 = "/info" |
||
657 | SLASH_INFORMANT4 = "/inf" |
||
658 | SlashCmdList["INFORMANT"] = cmdHandler |
||
659 | ]]); |
||
660 | Stubby.RegisterBootCode("Informant", "Triggers", [[ |
||
661 | local loadType = Stubby.GetConfig("Informant", "LoadType") |
||
662 | if (loadType == "always") then |
||
663 | LoadAddOn("Informant") |
||
664 | else |
||
665 | Stubby.Print("]].._INFM('MesgNotLoaded')..[["); |
||
666 | end |
||
667 | ]]); |
||
668 | end |
||
669 | |||
670 | function onVariablesLoaded() |
||
671 | setFilterDefaults() |
||
672 | |||
673 | InformantFrameTitle:SetText(_INFM('FrameTitle')) |
||
674 | |||
675 | if (InformantConfig.position) then |
||
676 | InformantFrame:ClearAllPoints() |
||
677 | InformantFrame:SetPoint("CENTER", UIParent, "BOTTOMLEFT", InformantConfig.position.x, InformantConfig.position.y) |
||
678 | end |
||
679 | |||
680 | if (not InformantConfig.welcomed) then |
||
681 | clear() |
||
682 | addLine(_INFM('Welcome')) |
||
683 | InformantConfig.welcomed = true |
||
684 | end |
||
685 | |||
686 | -- Restore key bindings |
||
687 | -- This workaround is required for LoadOnDemand addons since their saved |
||
688 | -- bindings are deleted upon login. |
||
689 | local profile = getKeyBindProfile(); |
||
690 | if (InformantConfig and InformantConfig.bindings) then |
||
691 | if (not InformantConfig.bindings[profile]) then profile = 'global'; end |
||
692 | if (InformantConfig.bindings[profile]) then |
||
693 | for _,key in ipairs(InformantConfig.bindings[profile]) do |
||
694 | SetBinding(key, 'INFORMANT_POPUPDOWN') |
||
695 | end |
||
696 | end |
||
697 | end |
||
698 | this:RegisterEvent("UPDATE_BINDINGS") -- Monitor changes to bindings |
||
699 | |||
700 | Informant.InitCommands() |
||
701 | end |
||
702 | |||
703 | function onEvent(event) |
||
704 | if (event == "ADDON_LOADED" and string.lower(arg1) == "informant") then |
||
705 | onVariablesLoaded() |
||
706 | this:UnregisterEvent("ADDON_LOADED") |
||
707 | elseif (event == "UPDATE_BINDINGS") then |
||
708 | -- Store key bindings for Informant |
||
709 | local key1, key2 = GetBindingKey('INFORMANT_POPUPDOWN'); |
||
710 | local profile = getKeyBindProfile(); |
||
711 | |||
712 | if (not InformantConfig.bindings) then InformantConfig.bindings = {}; end |
||
713 | if (not InformantConfig.bindings[profile]) then InformantConfig.bindings[profile] = {}; end |
||
714 | |||
715 | InformantConfig.bindings[profile][1] = key1; |
||
716 | InformantConfig.bindings[profile][2] = key2; |
||
717 | end |
||
718 | end |
||
719 | |||
720 | function frameActive(isActive) |
||
721 | if (isActive) then |
||
722 | scrollUpdate(0) |
||
723 | end |
||
724 | end |
||
725 | |||
726 | function getRowCount() |
||
727 | return table.getn(lines) |
||
728 | end |
||
729 | |||
730 | function scrollUpdate(offset) |
||
731 | local numLines = getRowCount() |
||
732 | if (numLines > 25) then |
||
733 | if (not offset) then |
||
734 | offset = FauxScrollFrame_GetOffset(InformantFrameScrollBar) |
||
735 | else |
||
736 | if (offset > numLines - 25) then offset = numLines - 25 end |
||
737 | FauxScrollFrame_SetOffset(InformantFrameScrollBar, offset) |
||
738 | end |
||
739 | else |
||
740 | offset = 0 |
||
741 | end |
||
742 | local line |
||
743 | for i=1, 25 do |
||
744 | line = lines[i+offset] |
||
745 | local f = getglobal("InformantFrameText"..i) |
||
746 | if (line) then |
||
747 | f:SetText(line) |
||
748 | f:Show() |
||
749 | else |
||
750 | f:Hide() |
||
751 | end |
||
752 | end |
||
753 | if (numLines > 25) then |
||
754 | FauxScrollFrame_Update(InformantFrameScrollBar, numLines, 25, numLines) |
||
755 | InformantFrameScrollBar:Show() |
||
756 | else |
||
757 | InformantFrameScrollBar:Hide() |
||
758 | end |
||
759 | end |
||
760 | |||
761 | function testWrap(text) |
||
762 | InformantFrameTextTest:SetText(text) |
||
763 | if (InformantFrameTextTest:GetWidth() < InformantFrame:GetWidth() - 20) then |
||
764 | return text, "" |
||
765 | end |
||
766 | |||
767 | local pos, test, best, rest |
||
768 | best = text |
||
769 | rest = nil |
||
770 | pos = string.find(text, " ") |
||
771 | while (pos) do |
||
772 | test = string.sub(text, 1, pos-1) |
||
773 | InformantFrameTextTest:SetText(test) |
||
774 | if (InformantFrameTextTest:GetWidth() < InformantFrame:GetWidth() - 20) or (not rest) then |
||
775 | best = test |
||
776 | rest = string.sub(test, pos+1) |
||
777 | else |
||
778 | break |
||
779 | end |
||
780 | pos = string.find(text, " ", pos+1) |
||
781 | end |
||
782 | return best, rest |
||
783 | end |
||
784 | |||
785 | function addLine(text, color, level) |
||
786 | if (text == nil) then return end |
||
787 | if (not level) then level = 1 end |
||
788 | if (level > 100) then |
||
789 | return |
||
790 | end |
||
791 | |||
792 | if (type(text) == "table") then |
||
793 | for pos, line in text do |
||
794 | addLine(line, color, level) |
||
795 | end |
||
796 | return |
||
797 | end |
||
798 | |||
799 | if (not text) then |
||
800 | table.insert(lines, "nil") |
||
801 | else |
||
802 | local best, rest = testWrap(text) |
||
803 | if (color) then |
||
804 | table.insert(lines, string.format("|cff%s%s|r", color, best)) |
||
805 | else |
||
806 | table.insert(lines, best) |
||
807 | end |
||
808 | if (rest) and (rest ~= "") then |
||
809 | addLine(rest, color, level+1) |
||
810 | end |
||
811 | end |
||
812 | scrollUpdate() |
||
813 | end |
||
814 | |||
815 | function clear() |
||
816 | lines = {} |
||
817 | scrollUpdate() |
||
818 | end |
||
819 | |||
820 | function setFilterDefaults() |
||
821 | if (not InformantConfig.filters) then InformantConfig.filters = {}; end |
||
822 | for k,v in pairs(filterDefaults) do |
||
823 | if (InformantConfig.filters[k] == nil) then |
||
824 | InformantConfig.filters[k] = v; |
||
825 | end |
||
826 | end |
||
827 | end |
||
828 | |||
829 | -- Key binding helper functions |
||
830 | |||
831 | function getKeyBindProfile() |
||
832 | if (IsAddOnLoaded("PerCharBinding")) then |
||
833 | return GetRealmName() .. ":" .. UnitName("player") |
||
834 | end |
||
835 | return 'global' |
||
836 | end |
||
837 | |||
838 | -- GLOBAL OBJECT |
||
839 | |||
840 | Informant = { |
||
841 | version = INFORMANT_VERSION, |
||
842 | GetItem = getItem, |
||
843 | GetRowCount = getRowCount, |
||
844 | AddLine = addLine, |
||
845 | Clear = clear, |
||
846 | ShowHideInfo = showHideInfo, |
||
847 | |||
848 | -- These functions are only meant for internal use. |
||
849 | SetSkills = setSkills, |
||
850 | SetRequirements = setRequirements, |
||
851 | SetVendors = setVendors, |
||
852 | SetDatabase = setDatabase, |
||
853 | FrameActive = frameActive, |
||
854 | FrameLoaded = frameLoaded, |
||
855 | ScrollUpdate = scrollUpdate, |
||
856 | GetFilter = getFilter, |
||
857 | GetFilterVal = getFilterVal, |
||
858 | GetLocale = getLocale, |
||
859 | OnEvent = onEvent, |
||
860 | SetFilter = setFilter, |
||
861 | SetFilterDefaults = setFilterDefaults, |
||
862 | } |
||
863 |