1 QuestHelper_File
["main.lua"] = "Development Version"
2 QuestHelper_Loadtime
["main.lua"] = GetTime()
4 local version_string
= QuestHelper_File
["main.lua"] -- we pretty much save this only so we can inform the user that they're using a beta version
6 -- Just to make sure it's always 'seen' (there's nothing that can be seen, but still...), and therefore always updating.
7 QuestHelper
:SetFrameStrata("TOOLTIP")
9 QuestHelper_CharVersion
= 1
10 QuestHelper_Locale
= GetLocale() -- This variable is used only for the collected data, and has nothing to do with displayed text.
11 QuestHelper_Quests
= {}
12 QuestHelper_Objectives
= {}
17 local QuestHelper_DefaultPref
=
22 filter_blocked
=false, -- Hides blocked objectives, such as quest turn-ins for incomplete quests
23 filter_watched
=false, -- Limits to Watched objectives
26 filter_wintergrasp
=true,
27 filter_raid_accessible
=true,
30 track_minimized
=false,
46 tomtom_wp_new
= false,
51 metric
= (QuestHelper_Locale
~= "enUS" and QuestHelper_Locale
~= "esMX"),
53 locale
= GetLocale(), -- This variable is used for display purposes, and has nothing to do with the collected data.
54 perf_scale_2
= 1, -- How much background processing can the current machine handle? Higher means more load, lower means better performance.
55 perfload_scale
= 1, -- Performance scale to use on startup
61 -- We do it here also in case things decide they care about preferences before the init function is called. Shouldn't happen, but maybe does.
62 setmetatable(QuestHelper_Pref
, {__index
=QuestHelper_DefaultPref
})
64 QuestHelper_FlightInstructors
= {}
65 QuestHelper_FlightLinks
= {}
66 QuestHelper_FlightRoutes
= {}
67 QuestHelper_KnownFlightRoutes
= {}
68 QuestHelper_SeenRealms
= {}
70 QuestHelper
.tooltip
= CreateFrame("GameTooltip", "QuestHelperTooltip", nil, "GameTooltipTemplate")
71 QuestHelper
.objective_objects
= {}
72 QuestHelper
.user_objectives
= {}
73 QuestHelper
.quest_objects
= {}
74 QuestHelper
.player_level
= 1
75 QuestHelper
.locale
= QuestHelper_Locale
77 QuestHelper
.faction
= (UnitFactionGroup("player") == "Alliance" and 1) or
78 (UnitFactionGroup("player") == "Horde" and 2)
80 assert(QuestHelper
.faction
)
82 QuestHelper
.font
= {serif
=GameFontNormal
:GetFont(), sans
=ChatFontNormal
:GetFont(), fancy
=QuestTitleFont
:GetFont()}
84 function QuestHelper
:GetFontPath(list_string
, font
)
86 for name
in string.gmatch(list_string
, "[^;]+") do
87 if font
:SetFont(name
, 10) then
89 elseif font
:SetFont("Interface\\AddOns\\QuestHelper\\Fonts\\"..name
, 10) then
90 return "Interface\\AddOns\\QuestHelper\\Fonts\\"..name
96 function QuestHelper
:SetLocaleFonts()
101 local font
= self
:CreateText(self
)
103 if QuestHelper_Locale
~= QuestHelper_Pref
.locale
then
104 -- Only use alternate fonts if using a language the client wasn't intended for.
105 local replacements
= QuestHelper_SubstituteFonts
[QuestHelper_Pref
.locale
]
107 self
.font
.sans
= self
:GetFontPath(replacements
.sans
, font
)
108 self
.font
.serif
= self
:GetFontPath(replacements
.serif
, font
)
109 self
.font
.fancy
= self
:GetFontPath(replacements
.fancy
, font
)
113 self
.font
.sans
= self
.font
.sans
or self
:GetFontPath(QuestHelper_Pref
.locale
.."_sans.ttf", font
)
114 self
.font
.serif
= self
.font
.serif
or self
:GetFontPath(QuestHelper_Pref
.locale
.."_serif.ttf", font
) or self
.font
.sans
115 self
.font
.fancy
= self
.font
.fancy
or self
:GetFontPath(QuestHelper_Pref
.locale
.."_fancy.ttf", font
) or self
.font
.serif
117 self
:ReleaseText(font
)
119 self
.font
.sans
= self
.font
.sans
or ChatFontNormal
:GetFont()
120 self
.font
.serif
= self
.font
.serif
or GameFontNormal
:GetFont()
121 self
.font
.fancy
= self
.font
.fancy
or QuestTitleFont
:GetFont()
123 -- Need to change the font of the chat frame, for any messages that QuestHelper displays.
124 -- This should do nothing if not using an alternate font.
125 --DEFAULT_CHAT_FRAME:SetFont(self.font.sans, select(2, DEFAULT_CHAT_FRAME:GetFont()))
126 -- what why did we ever do this
129 QuestHelper
.route
= {}
130 QuestHelper
.to_add
= {}
131 QuestHelper
.to_remove
= {}
132 QuestHelper
.quest_log
= {}
133 QuestHelper
.pos
= {nil, {}, 0, 0, 1, "You are here.", 0}
134 QuestHelper
.sharing
= false -- Will be set to true when sharing with at least one user.
136 function QuestHelper
.tooltip
:GetPrevLines() -- Just a helper to make life easier.
137 local last
= self
:NumLines()
138 local name
= self
:GetName()
139 return _G
[name
.."TextLeft"..last
], _G
[name
.."TextRight"..last
]
142 function QuestHelper
:SetTargetLocation(i
, x
, y
, toffset
)
143 -- Informs QuestHelper that you're going to be at some location in toffset seconds.
144 local c
, z
= unpack(QuestHelper_ZoneLookup
[i
])
146 self
.target
= self
:CreateTable()
147 self
.target
[2] = self
:CreateTable()
149 self
.target_time
= time()+(toffset
or 0)
151 x
, y
= self
.Astrolabe
:TranslateWorldMapPosition(c
, z
, x
, y
, c
, 0)
152 self
.target
[1] = self
.zone_nodes
[i
]
153 self
.target
[3] = x
* self
.continent_scales_x
[c
]
154 self
.target
[4] = y
* self
.continent_scales_y
[c
]
156 self
:SetTargetLocationRecalculate()
159 function QuestHelper
:SetTargetLocationRecalculate()
161 for i
, n
in ipairs(self
.target
[1]) do
162 local a
, b
= n
.x
-self
.target
[3], n
.y
-self
.target
[4]
163 self
.target
[2][i
] = math
.sqrt(a
*a
+b
*b
)
168 function QuestHelper
:UnsetTargetLocation()
169 -- Unsets the target set above.
171 self
:ReleaseTable(self
.target
[2])
172 self
:ReleaseTable(self
.target
)
174 self
.target_time
= nil
178 local interruptcount
= 0 -- counts how many "played gained control" messages we recieve, used for flight paths
179 local init_cartographer_later
= false
183 local please_submit_enabled
= true
184 local please_submit_initted
= false
186 local spawned
= false
187 QH_Event("ADDON_LOADED", function (addonid
)
188 if addonid
~= "QuestHelper" then return end
190 -- ONLY FAST STUFF ALLOWED IN HERE
192 -- Use DefaultPref as fallback for unset preference keys.
193 setmetatable(QuestHelper_Pref
, {__index
=QuestHelper_DefaultPref
})
194 QuestHelper
: Assert(QuestHelper_Pref
.perfload_scale
) -- if this fails, something is very botched
196 if not QuestHelper_Pref
.track
or QuestHelper_Pref
.hide
then
197 QuestHelper
:HideTracker()
199 QuestHelper
:ShowTracker() -- to respect the minimized setting
202 local self
= QuestHelper
-- whee hack hack hack
204 QuestHelper_Loadtime
["init2_start"] = GetTime()
206 local file_problem_version
= false
208 local expected_version
= GetAddOnMetadata("QuestHelper", "Version")
210 local expected_files
=
212 ["bst_pre.lua"] = true,
213 ["bst_post.lua"] = true,
214 ["bst_astrolabe.lua"] = true,
215 ["bst_ctl.lua"] = true,
216 ["bst_libaboutpanel.lua"] = true,
217 ["bst_range.lua"] = true,
219 ["manager_event.lua"] = true,
220 ["manager_achievement.lua"] = true,
221 ["manager_completed.lua"] = true,
223 ["upgrade.lua"] = true,
225 ["recycle.lua"] = true,
226 ["objective.lua"] = true,
227 ["quest.lua"] = true,
228 ["utility.lua"] = true,
229 ["dodads.lua"] = true,
230 ["dodads_triangles.lua"] = true,
231 ["teleport.lua"] = true,
232 ["pathfinding.lua"] = true,
233 ["routing.lua"] = true,
234 ["custom.lua"] = true,
238 ["mapbutton.lua"] = true,
240 ["pattern.lua"] = true,
241 ["flightpath.lua"] = true,
242 ["tracker.lua"] = true,
243 ["objtips.lua"] = true,
244 ["cartographer.lua"] = true,
245 ["cartographer_is_terrible.lua"] = true,
246 ["tomtom.lua"] = true,
247 ["textviewer.lua"] = true,
248 ["error.lua"] = true,
249 ["timeslice.lua"] = true,
252 ["tooltip.lua"] = true,
253 ["arrow.lua"] = true,
254 ["radar.lua"] = true,
256 ["static.lua"] = true,
257 ["static_1.lua"] = true,
258 ["static_2.lua"] = true,
259 ["static_deDE.lua"] = true,
260 ["static_deDE_1.lua"] = true,
261 ["static_deDE_2.lua"] = true,
262 ["static_enUS.lua"] = true,
263 ["static_enUS_1.lua"] = true,
264 ["static_enUS_2.lua"] = true,
265 ["static_esES.lua"] = true,
266 ["static_esES_1.lua"] = true,
267 ["static_esES_2.lua"] = true,
268 ["static_esMX.lua"] = true,
269 ["static_esMX_1.lua"] = true,
270 ["static_esMX_2.lua"] = true,
271 ["static_frFR.lua"] = true,
272 ["static_frFR_1.lua"] = true,
273 ["static_frFR_2.lua"] = true,
274 ["static_koKR.lua"] = true,
275 ["static_koKR_1.lua"] = true,
276 ["static_koKR_2.lua"] = true,
277 ["static_ruRU.lua"] = true,
278 ["static_ruRU_1.lua"] = true,
279 ["static_ruRU_2.lua"] = true,
280 ["static_zhTW.lua"] = true,
281 ["static_zhTW_1.lua"] = true,
282 ["static_zhTW_2.lua"] = true,
284 ["collect.lua"] = true,
285 ["collect_achievement.lua"] = true,
286 ["collect_lzw.lua"] = true,
287 ["collect_traveled.lua"] = true,
288 ["collect_zone.lua"] = true,
289 ["collect_location.lua"] = true,
290 ["collect_merger.lua"] = true,
291 ["collect_monster.lua"] = true,
292 ["collect_item.lua"] = true,
293 ["collect_object.lua"] = true,
294 ["collect_loot.lua"] = true,
295 ["collect_patterns.lua"] = true,
296 ["collect_flight.lua"] = true,
297 ["collect_util.lua"] = true,
298 ["collect_quest.lua"] = true,
299 ["collect_equip.lua"] = true,
300 ["collect_notifier.lua"] = true,
301 ["collect_bitstream.lua"] = true,
302 ["collect_spec.lua"] = true,
303 ["collect_upgrade.lua"] = true,
304 ["collect_merchant.lua"] = true,
305 ["collect_warp.lua"] = true,
307 ["filter_core.lua"] = true,
308 ["filter_base.lua"] = true,
310 ["routing_debug.lua"] = true,
311 ["routing_loc.lua"] = true,
312 ["routing_route.lua"] = true,
313 ["routing_core.lua"] = true,
314 ["routing_controller.lua"] = true,
315 ["routing_hidden.lua"] = true,
317 ["director_quest.lua"] = true,
318 ["director_achievement.lua"] = true,
319 ["director_find.lua"] = true,
321 ["db_get.lua"] = true,
323 ["graph_core.lua"] = true,
324 ["graph_flightpath.lua"] = true,
326 ["AstrolabeQH/Astrolabe.lua"] = true,
327 ["AstrolabeQH/AstrolabeMapMonitor.lua"] = true,
330 local uninstallederr
= ""
332 for file
, version
in pairs(QuestHelper_File
) do
333 if not expected_files
[file
] then
334 local errmsg
= "Unexpected QuestHelper file: "..file
335 DEFAULT_CHAT_FRAME
:AddMessage(errmsg
)
336 uninstallederr
= uninstallederr
.. " " .. errmsg
.. "\n"
337 file_problem_version
= true
338 elseif version
~= expected_version
then
339 local errmsg
= "Wrong version of QuestHelper file: "..file
.." (found '"..version
.."', should be '"..expected_version
.."')"
340 DEFAULT_CHAT_FRAME
:AddMessage(errmsg
)
341 uninstallederr
= uninstallederr
.. " " .. errmsg
.. "\n"
342 if version
~= "Development Version" and expected_version
~= "Development Version" then
343 -- Developers are allowed to mix dev versions with release versions
344 file_problem_version
= true
349 for file
in pairs(expected_files
) do
350 if not QuestHelper_File
[file
] then
351 local errmsg
= "Missing QuestHelper file: "..file
352 DEFAULT_CHAT_FRAME
:AddMessage(errmsg
)
353 uninstallederr
= uninstallederr
.. " " .. errmsg
.. "\n"
354 if not (expected_version
== "Development Version" and file
:match("static.*")) then file_problem_version
= true end
358 -- Don't need this table anymore.
359 QuestHelper_File
= nil
361 if QuestHelper_StaticData
and not QuestHelper_StaticData
[GetLocale()] then
362 local errmsg
= "Static data does not seem to exist"
363 DEFAULT_CHAT_FRAME
:AddMessage(errmsg
)
365 uninstallederr
= uninstallederr
.. " " .. errmsg
.. "\n"
366 file_problem_version
= true
369 if file_problem_version
then
370 QH_fixedmessage(QHText("PLEASE_RESTART"))
371 QuestHelper_ErrorCatcher_ExplicitError(false, "not-installed-properly" .. "\n" .. uninstallederr
)
372 QuestHelper
= nil -- Just in case anybody else is checking for us, we're not home
376 if not GetCategoryList
or not GetQuestLogSpecialItemInfo
or not WatchFrame_RemoveObjectiveHandler
then
377 QH_fixedmessage(QHText("PRIVATE_SERVER"))
378 QuestHelper_ErrorCatcher_ExplicitError(false, "error id cakbep ten T")
383 if not DongleStub
or not QH_Astrolabe_Ready
then
384 QH_fixedmessage(QHText("NOT_UNZIPPED_CORRECTLY"))
385 QuestHelper_ErrorCatcher_ExplicitError(false, "not-unzipped-properly")
386 QuestHelper
= nil -- Just in case anybody else is checking for us, we're not home
390 QuestHelper_ErrorCatcher_CompletelyStarted()
392 if not QuestHelper_StaticData
then
393 -- If there is no static data for some mysterious reason, create an empty table so that
394 -- other parts of the code can carry on as usual, using locally collected data if it exists.
395 QuestHelper_StaticData
= {}
398 QHFormatSetLocale(QuestHelper_Pref
.locale
or GetLocale())
400 if not QuestHelper_UID
then
401 QuestHelper_UID
= self
:CreateUID()
403 QuestHelper_SaveDate
= time()
406 QH_Timeslice_Add(function ()
407 QuestHelper_Loadtime
["init3_start"] = GetTime()
409 QuestHelper
.loading_main
= QuestHelper
.CreateLoadingCounter()
411 QuestHelper
.loading_init3
= QuestHelper
.loading_main
:MakeSubcategory(0.3)
412 QuestHelper
.loading_flightpath
= QuestHelper
.loading_main
:MakeSubcategory(1)
413 QuestHelper
.loading_preroll
= QuestHelper
.loading_main
:MakeSubcategory(1)
417 -- This is where the slow stuff goes
418 QuestHelper_BuildZoneLookup()
422 if QuestHelper_Locale
~= GetLocale() then
423 self
:TextOut(QHText("LOCALE_ERROR"))
427 if not self
:ZoneSanity() then
428 self
:TextOut(QHFormat("ZONE_LAYOUT_ERROR", expected_version
))
429 QH_fixedmessage(QHFormat("ZONE_LAYOUT_ERROR", expected_version
))
434 QuestHelper_UpgradeDatabase(_G
)
435 QuestHelper_UpgradeComplete()
437 if QuestHelper_IsPolluted(_G
) then
438 self
:TextOut(QHFormat("NAG_POLLUTED"))
439 self
:Purge(nil, true, true)
442 local signature
= expected_version
.. " on " .. GetBuildInfo()
443 QuestHelper_Quests
[signature
] = QuestHelper_Quests
[signature
] or {}
444 QuestHelper_Objectives
[signature
] = QuestHelper_Objectives
[signature
] or {}
445 QuestHelper_FlightInstructors
[signature
] = QuestHelper_FlightInstructors
[signature
] or {}
446 QuestHelper_FlightRoutes
[signature
] = QuestHelper_FlightRoutes
[signature
] or {}
448 QuestHelper_Quests_Local
= QuestHelper_Quests
[signature
]
449 QuestHelper_Objectives_Local
= QuestHelper_Objectives
[signature
]
450 QuestHelper_FlightInstructors_Local
= QuestHelper_FlightInstructors
[signature
]
451 QuestHelper_FlightRoutes_Local
= QuestHelper_FlightRoutes
[signature
]
453 QuestHelper_SeenRealms
[GetRealmName()] = true -- some attempt at tracking private servers
455 QuestHelper
.loading_init3
:SetPercentage(0.1)
457 QuestHelper
.loading_init3
:SetPercentage(0.5)
459 QuestHelper
.loading_init3
:SetPercentage(0.9)
461 self
.player_level
= UnitLevel("player")
463 self
:SetLocaleFonts()
465 if QuestHelper_Pref
.share
and not QuestHelper_Pref
.solo
then
469 if QuestHelper_Pref
.hide
then
470 self
.map_overlay
:Hide()
473 self
:HandlePartyChange()
477 for locale
in pairs(QuestHelper_StaticData
) do
478 if locale
~= self
.locale
then
479 -- Will delete references to locales you don't use.
480 QuestHelper_StaticData
[locale
] = nil
481 _G
["QuestHelper_StaticData_" .. locale
] = nil
485 local static
= QuestHelper_StaticData
[self
.locale
]
488 if static
.flight_instructors
then for faction
in pairs(static
.flight_instructors
) do
489 if faction
~= self
.faction
then
490 -- Will delete references to flight instructors that don't belong to your faction.
491 static
.flight_instructors
[faction
] = nil
495 if static
.quest
then for faction
in pairs(static
.quest
) do
496 if faction
~= self
.faction
then
497 -- Will delete references to quests that don't belong to your faction.
498 static
.quest
[faction
] = nil
503 -- Adding QuestHelper_CharVersion, so I know if I've already converted this characters saved data.
504 if not QuestHelper_CharVersion
then
505 -- Changing per-character flight routes, now only storing the flight points they have,
506 -- will attempt to guess the routes from this.
509 for i
, l
in pairs(QuestHelper_KnownFlightRoutes
) do
510 for key
in pairs(l
) do
515 QuestHelper_KnownFlightRoutes
= routes
517 -- Deleting the player's home again.
518 -- But using the new CharVersion variable I'm adding is cleaner that what I was doing, so I'll go with it.
519 QuestHelper_Home
= nil
520 QuestHelper_CharVersion
= 1
523 if not QuestHelper_Home
then
524 -- Not going to bother complaining about the player's home not being set, uncomment this when the home is used in routing.
525 -- self:TextOut(QHText("HOME_NOT_KNOWN"))
528 if QuestHelper_Pref
.map_button
then
529 QuestHelper
:InitMapButton()
532 if QuestHelper_Pref
.cart_wp_new
then
533 init_cartographer_later
= true
536 if QuestHelper_Pref
.tomtom_wp_new
then
540 self
.tracker
:SetScale(QuestHelper_Pref
.track_scale
)
542 local version
= GetAddOnMetadata("QuestHelper", "Version") or "Unknown"
544 local major
, minor
= (version_string
or ""):match("^(%d+)%.(%d+)")
545 major
, minor
= tonumber(major
), tonumber(minor
)
547 -- For versions before 0.82, we're changing the default level offset to 3.
548 if major
== 0 and minor
and minor
< 82 and QuestHelper_Pref
.level
== 2 then
549 QuestHelper_Pref
.level
= nil
552 -- For versions before 0.84...
553 if major
== 0 and minor
and minor
< 84 then
554 -- remove all keys that match their default setting.
555 for key
, val
in pairs(QuestHelper_DefaultPref
) do
556 if QuestHelper_Pref
[key
] == val
then
557 QuestHelper_Pref
[key
] = nil
562 QH_Hook(self
, "OnUpdate", self
.OnUpdate
)
564 -- Seems to do its own garbage collection pass before fully loading, so I'll just rely on that
565 --collectgarbage("collect") -- Free everything we aren't using.
568 if self.debug_objectives then
569 for name, data in pairs(self.debug_objectives) do
570 self:LoadDebugObjective(name, data)
576 QH_Arrow_SetTextScale()
579 QH_Timeslice_Add(function ()
581 self.Routing:Initialize() -- Set up the routing task
582 end, "init")]] -- FUCK YOU BOXBOT
584 --[[ -- This is just an example of how the WoW profiler biases its profiles heavily.
590 for x = 0, 130000000, 1 do
596 for x = 0, 12000000, 1 do
603 for x = 0, 1200000, 1 do
611 local ta = debugprofilestop()
613 local tb = debugprofilestop()
615 local tc = debugprofilestop()
617 QuestHelper:TextOut(string.format("%d %d %d", ta, tb - ta, tc - tb))
618 QuestHelper:TextOut(string.format("%d %d", GetFunctionCPUUsage(A), GetFunctionCPUUsage(B)))
620 --/script SetCVar("scriptProfile", value)]]
622 LibStub("LibAboutPanelQH").new(nil, "QuestHelper")
625 QH_Event("CHAT_MSG_ADDON", function (...)
626 if arg1
== "QHpr" and arg4
~= UnitName("player") then
627 QH_Questcomm_Msg(arg2
, arg4
)
631 QH_Event({"PARTY_MEMBERS_CHANGED", "UNIT_LEVEL", "RAID_ROSTER_UPDATE"}, function ()
632 QH_Filter_Group_Sync()
633 QH_Route_Filter_Rescan("filter_quest_level")
634 --QH_Route_Filter_Rescan("filter_quest_group")
635 --QH_Route_Filter_Rescan("filter_quest_raid_accessible") -- These should be in right now, but for simplicity's sake we're actually scanning everything when we get a rescan request. So they're unnecessary. PUT THEM BACK should they become necessary.
638 QH_Event({"PARTY_MEMBERS_CHANGED", "RAID_ROSTER_UPDATE"}, function ()
642 QH_Event("PLAYER_LEVEL_UP", function ()
643 self
.player_level
= arg1
644 QH_Route_Filter_Rescan("filter_quest_level")
647 QH_Event("TAXIMAP_OPENED", function ()
651 QH_Event({"ZONE_CHANGED", "ZONE_CHANGED_INDOORS", "ZONE_CHANGED_NEW_AREA"}, function()
652 QH_Route_Filter_Rescan(nil, true)
655 QH_Event("CHAT_MSG_CHANNEL_NOTICE", function()
656 if please_submit_enabled
and not please_submit_initted
then
657 please_submit_enabled
= QHNagInit()
658 startup_time
= GetTime()
659 please_submit_initted
= true
663 QuestHelper
.loading_init3
:SetPercentage(1.0) -- victory
665 QuestHelper_Loadtime
["init3_end"] = GetTime()
668 QuestHelper_Loadtime
["init2_end"] = GetTime()
673 function QuestHelper
:OnEvent(event
)
674 local tstart
= GetTime()
677 if event == "GOSSIP_SHOW" then
678 local name, id = UnitName("npc"), self:GetUnitID("npc")
680 self:GetObjective("monster", name).o.id = id
681 --self:TextOut("NPC: "..name.." = "..id)
685 --[[if event == "PLAYER_TARGET_CHANGED" then
686 local name, id = UnitName("target"), self:GetUnitID("target")
688 self:GetObjective("monster", name).o.id = id
689 --self:TextOut("Target: "..name.." = "..id)
692 if UnitExists("target") and UnitIsVisible("target") and UnitCreatureType("target") ~= "Critter" and not UnitIsPlayer("target") and not UnitPlayerControlled("target") then
693 local index, x, y = self:UnitPosition("target")
695 if index then -- Might not have a position if inside an instance.
698 -- Modify the weight based on how far they are from us.
699 -- We don't know the exact location (using our own location), so the farther, the less sure we are that it's correct.
700 if CheckInteractDistance("target", 3) then w = 1
701 elseif CheckInteractDistance("target", 2) then w = 0.89
702 elseif CheckInteractDistance("target", 1) or CheckInteractDistance("target", 4) then w = 0.33 end
704 local monster_objective = self:GetObjective("monster", UnitName("target"))
705 self:AppendObjectivePosition(monster_objective, index, x, y, w)
707 monster_objective.o.faction = (UnitFactionGroup("target") == "Alliance" and 1) or
708 (UnitFactionGroup("target") == "Horde" and 2) or nil
710 local level = UnitLevel("target")
711 if level and level >= 1 then
712 local w = monster_objective.o.levelw or 0
713 monster_objective.o.level = ((monster_objective.o.level or 0)*w+level)/(w+1)
714 monster_objective.o.levelw = w+1
720 --[[if event == "LOOT_OPENED" then
721 local target = UnitName("target")
722 if target and UnitIsDead("target") and UnitCreatureType("target") ~= "Critter" and not UnitIsPlayer("target") and not UnitPlayerControlled("target") then
723 local index, x, y = self:UnitPosition("target")
725 local monster_objective = self:GetObjective("monster", target)
726 monster_objective.o.looted = (monster_objective.o.looted or 0) + 1
728 if index then -- Might not have a position if inside an instance.
729 self:AppendObjectivePosition(monster_objective, index, x, y)
732 for i = 1, GetNumLootItems() do
733 local icon, name, number, rarity = GetLootSlotInfo(i)
735 if number and number >= 1 then
736 self:AppendItemObjectiveDrop(self:GetObjective("item", name), name, target, number)
738 local total = (name:match(COPPER_AMOUNT:gsub("%%d", "%(%%d+%)")) or 0) +
739 (name:match(SILVER_AMOUNT:gsub("%%d", "%(%%d+%)")) or 0) * 100 +
740 (name:match(GOLD_AMOUNT:gsub("%%d", "%(%%d+%)")) or 0) * 10000
743 self:AppendObjectiveDrop(self:GetObjective("item", "money"), target, total)
749 local container = nil
751 -- Go through the players inventory and look for a locked item, we're probably looting it.
752 for bag = 0,NUM_BAG_SLOTS do
753 for slot = 1,GetContainerNumSlots(bag) do
754 local link = GetContainerItemLink(bag, slot)
755 if link and select(3, GetContainerItemInfo(bag, slot)) then
756 if container == nil then
757 -- Found a locked item and haven't previously assigned to container, assign its name, or false if we fail to parse it.
758 container = select(3, string.find(link, "|h%[(.+)%]|h|r")) or false
760 -- Already tried to assign to a container. If there are multiple locked items, we give up.
768 local container_objective = self:GetObjective("item", container)
769 container_objective.o.opened = (container_objective.o.opened or 0) + 1
771 for i = 1, GetNumLootItems() do
772 local icon, name, number, rarity = GetLootSlotInfo(i)
773 if name and number >= 1 then
774 self:AppendItemObjectiveContainer(self:GetObjective("item", name), container, number)
778 -- No idea where the items came from.
779 local index, x, y = self:PlayerPosition()
782 for i = 1, GetNumLootItems() do
783 local icon, name, number, rarity = GetLootSlotInfo(i)
784 if name and number >= 1 then
785 self:AppendItemObjectivePosition(self:GetObjective("item", name), name, index, x, y)
793 --[[if event == "CHAT_MSG_SYSTEM" then
794 local home_name = self:convertPattern(ERR_DEATHBIND_SUCCESS_S)(arg1)
797 self:TextOut(QHText("HOME_CHANGED"))
798 self:TextOut(QHText("WILL_RESET_PATH"))
800 local home = QuestHelper_Home
803 QuestHelper_Home = home
806 home[1], home[2], home[3], home[4] = self.i, self.x, self.y, home_name
807 self.defered_graph_reset = true
815 --[[if event == "QUEST_DETAIL" then
816 if not self.quest_giver then self.quest_giver = {} end
817 local npc = UnitName("npc")
819 -- Some NPCs aren't actually creatures, and so their positions might not be marked by PLAYER_TARGET_CHANGED.
820 local index, x, y = self:UnitPosition("npc")
822 if index then -- Might not have a position if inside an instance.
823 local npc_objective = self:GetObjective("monster", npc)
824 self:AppendObjectivePosition(npc_objective, index, x, y)
825 self.quest_giver[GetTitleText()] = npc
830 --[[if event == "QUEST_COMPLETE" or event == "QUEST_PROGRESS" then
831 local quest = GetTitleText()
833 local level, hash = self:GetQuestLevel(quest)
834 if not level or level < 1 then
835 --self:TextOut("Don't know quest level for ".. quest.."!")
838 local q = self:GetQuest(quest, level, hash)
844 local unit = UnitName("npc")
849 -- Some NPCs aren't actually creatures, and so their positions might not be marked by PLAYER_TARGET_CHANGED.
850 local index, x, y = self:UnitPosition("npc")
851 if index then -- Might not have a position if inside an instance.
852 local npc_objective = self:GetObjective("monster", unit)
853 self:AppendObjectivePosition(npc_objective, index, x, y)
855 elseif not q.o.finish then
856 local index, x, y = self:PlayerPosition()
857 if index then -- Might not have a position if inside an instance.
858 self:AppendObjectivePosition(q, index, x, y)
864 --[[if event == "MERCHANT_SHOW" then
865 local npc_name = UnitName("npc")
867 local npc_objective = self:GetObjective("monster", npc_name)
870 local item_name = GetMerchantItemInfo(index)
873 local item_objective = self:GetObjective("item", item_name)
874 if not item_objective.o.vendor then
875 item_objective.o.vendor = {npc_name}
878 for i, vendor in ipairs(item_objective.o.vendor) do
879 if npc_name == vendor then
885 table.insert(item_objective.o.vendor, npc_name)
895 if event
== "TAXIMAP_OPENED" then
899 --[[if event == "PLAYER_CONTROL_GAINED" then
900 interruptcount = interruptcount + 1
903 --[[if event == "BAG_UPDATE" then
904 for slot = 1,GetContainerNumSlots(arg1) do
905 local link = GetContainerItemLink(arg1, slot)
907 local id, name = select(3, string.find(link, "|Hitem:(%d+):.-|h%[(.-)%]|h"))
909 self:GetObjective("item", name).o.id = tonumber(id)
917 if event
== "ZONE_CHANGED" or event
== "ZONE_CHANGED_INDOORS" or event
== "ZONE_CHANGED_NEW_AREA" then
918 QH_Route_Filter_Rescan()
921 QH_Timeslice_Increment(GetTime() - tstart
, "event")
924 local map_shown_decay
= 0
925 local delayed_action
= 100
926 --local update_count = 0
930 QH_OnUpdate_High(function ()
931 local self
= QuestHelper
-- hoorj
932 local tstart
= GetTime()
935 if not QuestHelper_Loadtime
["onupdate"] then QuestHelper_Loadtime
["onupdate"] = GetTime() end
937 if false and frams
== 60 then
939 This is a |cffff8000beta of QuestHelper|r. Be warned: It may crash. It may lock up. It may give bad advice. It may spew errors. It shouldn't spam people, delete your hard-won epics, or make your computer catch on fire, but technically I'm giving no guarantees. |cffff8000If you want a polished, functioning product, close WoW, download the official QH release from curse.com, and use that.|r
941 Known bugs and issues include:
943 |cff40bbffNo support for "/qh find"|r
945 |cff40bbffNo support for in-party quest synchronization|r
947 These may not be fixed before the official 1.0 release - I'm hoping to get them all finished up in time for 1.1.
949 If you encounter any issue besides the ones listed here, please please please report it, if you're reading this you know how to get in contact with me anyway.
951 Thanks for testing!]], "QuestHelper " .. version_string
, 500, 20, 10)
954 --if frams == 5000 then please_submit_enabled = false end -- TOOK TOO LONG >:(
955 if please_submit_enabled
and startup_time
and startup_time
+ 10 < GetTime() then
956 QuestHelper
:TextOut(QHText("PLEASE_SUBMIT"))
958 please_submit_enabled
= false
960 QHUpdateNagTick() -- These probably shouldn't be in OnUpdate. Eventually I'll move them somewhere cleaner.
962 if init_cartographer_later
and Cartographer_Waypoints
then -- there has to be a better way to do this
963 init_cartographer_later
= false
964 if QuestHelper_Pref
.cart_wp_new
then
965 self
:EnableCartographer()
969 if not ontaxi
and UnitOnTaxi("player") then
972 elseif ontaxi
and not UnitOnTaxi("player") then
973 self
:flightEnded(interruptcount
> 1)
975 ontaxi
= UnitOnTaxi("player")
977 -- For now I'm ripping out the update_count code
978 --update_count = update_count - 1
979 --if update_count <= 0 then
981 -- Reset the update count for next time around; this will make sure the body executes every time
982 -- when perf_scale_2 >= 1, and down to 1 in 10 iterations when perf_scale_2 < 1, or when hidden.
983 --update_count = update_count + (QuestHelper_Pref.hide and 10 or 1/QuestHelper_Pref.perf_scale_2)
985 --if update_count < 0 then
986 -- Make sure the count doesn't go perpetually negative; don't know what will happen if it underflows.
990 if self
.Astrolabe
.WorldMapVisible
then
991 -- We won't trust that the zone returned by Astrolabe is correct until map_shown_decay is 0.
993 elseif map_shown_decay
> 0 then
994 map_shown_decay
= map_shown_decay
- 1
996 --SetMapToCurrentZone() -- not sure why this existed
999 --[[delayed_action = delayed_action - 1
1000 if delayed_action <= 0 then
1001 delayed_action = 100
1002 self:HandlePartyChange()
1005 local nc
, nz
, nx
, ny
= self
.Astrolabe
:GetCurrentPlayerPosition()
1008 if nc
and nc
~= -1 then -- We just want the raw data here, before we've done anything clever.
1009 tc
, tx
, ty
= self
.Astrolabe
:GetAbsoluteContinentPosition(nc
, nz
, nx
, ny
)
1010 QuestHelper
: Assert(tc
and tx
and ty
) -- is it true? nobody knows! :D
1013 if nc
and nc
== self
.c
and map_shown_decay
> 0 and self
.z
> 0 and self
.z
~= nz
then
1014 -- There's a chance Astrolable will return the wrong zone if you're messing with the world map, if you can
1015 -- be seen in that zone but aren't in it.
1016 local nnx
, nny
= self
.Astrolabe
:TranslateWorldMapPosition(nc
, nz
, nx
, ny
, nc
, self
.z
)
1017 if nnx
> 0 and nny
> 0 and nnx
< 1 and nny
< 1 then
1018 nz
, nx
, ny
= self
.z
, nnx
, nny
1022 if nc
and nc
> 0 and nz
== 0 and nc
== self
.c
and self
.z
> 0 then
1023 nx
, ny
= self
.Astrolabe
:TranslateWorldMapPosition(nc
, nz
, nx
, ny
, nc
, self
.z
)
1024 if nx
and ny
--[[and nx > -0.1 and ny > -0.1 and nx < 1.1 and ny < 1.1]] then -- removing the conditional because I think I can use the data even when it's a little wonky
1027 nc
, nz
, nx
, ny
= nil, nil, nil, nil
1031 if nc
and nz
> 0 and QuestHelper_IndexLookup
[nc
] then -- QuestHelper_IndexLookup is only initialized after we've finished the preinit step
1032 self
.c
, self
.z
, self
.x
, self
.y
= nc
, nz
, nx
, ny
1033 local upd_zone
= false
1034 if self
.i
~= QuestHelper_IndexLookup
[nc
][nz
] then upd_zone
= true end
1035 self
.i
= QuestHelper_IndexLookup
[nc
][nz
]
1036 if upd_zone
then QH_Route_Filter_Rescan("filter_zone") end
1039 if nc
and nz
and nx
and ny
and tc
and tx
and ty
then
1040 self
.collect_rc
, self
.collect_rz
, self
.collect_rx
, self
.collect_ry
= nc
, nz
, nx
, ny
1041 self
.collect_ac
, self
.collect_ax
, self
.collect_ay
= tc
, tx
, ty
1042 self
.collect_delayed
= false
1044 local ibi
= self
.InBrokenInstance
1045 if nc
< -77 then self
.InBrokenInstance
= true else self
.InBrokenInstance
= false end
1047 if ibi
and not self
.InBrokenInstance
then self
.minimap_marker
:OnUpdate(0) end -- poke
1049 self
.collect_delayed
= true
1050 self
.InBrokenInstance
= true
1053 if not UnitOnTaxi("player") and not UnitIsDeadOrGhost("player") then
1054 QuestHelper
.routing_ac
, QuestHelper
.routing_ax
, QuestHelper
.routing_ay
, QuestHelper
.routing_c
, QuestHelper
.routing_z
= QuestHelper
.collect_ac
, QuestHelper
.collect_ax
, QuestHelper
.collect_ay
, QuestHelper
.c
, QuestHelper
.z
1057 QH_Timeslice_Toggle("routing", not not self
.c
)
1059 self
:PumpCommMessages()
1063 -- Some or all of these may be nil. c,x,y should be enough for a location - c is the pure continent (currently either 0 or 3 for Azeroth or Outland, or -77 for the DK starting zone) and x,y are the coordinates within that continent.
1064 -- rc and rz are the continent and zone that Questhelper thinks it's within. For various reasons, this isn't perfect. TODO: Base it off the map zone name identifiers instead of the map itself?
1065 function QuestHelper
:Location_RawRetrieve()
1066 return self
.collect_delayed
, self
.collect_rc
, self
.collect_rz
, self
.collect_rx
, self
.collect_ry
1068 function QuestHelper
:Location_AbsoluteRetrieve()
1069 return self
.collect_delayed
, self
.collect_ac
, self
.collect_ax
, self
.collect_ay
1072 --QH_Hook(QuestHelper, "OnEvent", QuestHelper.OnEvent)