WoWInterface

WoWInterface (https://www.wowinterface.com/forums/index.php)
-   Lua/XML Help (https://www.wowinterface.com/forums/forumdisplay.php?f=16)
-   -   Is it possible to obtain quest title by questID ? (https://www.wowinterface.com/forums/showthread.php?t=46934)

AnrDaemon 07-25-13 04:15 AM

Is it possible to obtain quest title by questID ?
 
Is it possible to obtain quest title by questID ?
I'm digging through API, but with no result so far.

To clarify: Arbitrary questID. I have no idea, if character have the quest, or if it is even available to character.

ckaotik 07-25-13 12:21 PM

I have been wondering the same thing for quite a while and couldn't find anything either :(
Even addons like DataStore save the quest title to their database when accepting/completing quests or from the player's quest log.

Same goes for QuestIsDaily and QuestIsWeekly (both only available on quest dialogs) and GetQuestLink (quest log based). Would love to have a GetQuestInfo(questID) function, but so far no luck.

Seerah 07-25-13 01:06 PM

How about using this on a hidden tooltip object and reading the first line of the tooltip? http://wowprogramming.com/docs/widge...p/SetHyperlink

Phanx 07-25-13 01:47 PM

This is a perfect use-case for a metatable and tooltip scanning:

Code:

local MyScanningTooltip = CreateFrame("GameTooltip", "MyScanningTooltip", UIParent, "GameTooltipTemplate")

local QuestTitleFromID = setmetatable({}, { __index = function(t, id)
        MyScanningTooltip:SetOwner(UIParent, "ANCHOR_NONE")
        MyScanningTooltip:SetHyperlink("quest:"..id)
        local title = MyScanningTooltipTextLeft1:GetText()
        MyScanningTooltip:Hide()
        if title and title ~= RETRIEVING_DATA then
                t[id] = title
                return title
        end
end })

Put that at/near the top of your file, and then just do a simple table lookup with the ID to get the name:

Code:

print(QuestTitleFromID[30318])
-- prints "Chasing the Chicken"

If the ID is invalid, or your game client doesn't have the info yet and has to query the server (not sure if this can even happen for quests), you will get nil instead of the quest name; if you're sure your ID was valid, you can just look it up again and your client should have the data by then.

You can use the same technique to get the localized name of anything else where there is no relevant API (eg. if you want item or spell names, just use GetItemInfo or GetSpellInfo). For example, there was recently a thread demonstrating this technique for getting localized NPC names from their mobIDs.

semlar 07-25-13 02:28 PM

When you set the tooltip to a quest ID it has to request the information from the server if it hasn't been cached yet, it's similar to getting item information.

You can use OnTooltipSetQuest which triggers when the tooltip actually receives new information.

Note that the event can fire multiple times for the same quest because the tooltip may contain the name of items in the "Requirements" section and each item name requires another server request.

I had written a more complicated example that retrieved the entire quest text but there probably isn't any point in posting it.

AnrDaemon 07-25-13 10:37 PM

Does that mean that I can do something like

Lua Code:
  1. local frame = CreateFrame("GameTooltip", "MyPrivateStuff_QuestInfoTooltipFrame", UIParent, "GameTooltipTemplate")
  2.  
  3. function frame:GetQuestTitle()
  4.   local title = MyPrivateStuff_QuestInfoTooltipFrameTextLeft1:GetText()
  5.   DEFAULT_CHAT_FRAME:AddMessage(self["message"]:format(title))
  6.   self:SetScript("OnTooltipSetQuest", nil)
  7. end
  8.  
  9. -- Add some slashes sausage
  10. local function commandHandler(msg, self)
  11.   local argv = { strsplit(" ", strtrim(msg)) }
  12.   if argv[1] == "quest" then
  13.     if IsQuestFlaggedCompleted(argv[2]) then
  14.       frame["message"] = ("Quest |cffffff00|Hquest:%d|h[%%s]|h|r flagged as completed."):format(argv[2])
  15.     else
  16.       frame["message"] = ("Quest |cffffff00|Hquest:%d|h[%%s]|h|r is not completed or not available to character."):format(argv[2])
  17.     end
  18.     frame:SetScript("OnTooltipSetQuest", frame.GetQuestTitle)
  19.     frame:SetOwner(UIParent, "ANCHOR_NONE")
  20.     frame:SetHyperlink("quest:" .. argv[2])
  21.   end
  22. end
  23.  
  24. SlashCmdList["MYPRIVATESTUFF"] = commandHandler
  25. SLASH_MYPRIVATESTUFF1 = '/my'
? Anyone see anything apparently wrong with such logic? Or I can go for field testing? :)

AnrDaemon 07-26-13 01:00 AM

Aww, stupid... After bashing over a wall of air, it finally worked quite nicely.

Lua Code:
  1. local tooltip = CreateFrame("GameTooltip", "MyPrivateStuff_QTipFrame", UIParent, "GameTooltipTemplate")
  2.  
  3. function tooltip:GetQuestTitle()
  4.   local title = MyPrivateStuff_QTipFrameTextLeft1:GetText()
  5.   DEFAULT_CHAT_FRAME:AddMessage(self["message"]:format(title))
  6.   self:SetScript("OnTooltipSetQuest", nil)
  7. end
  8.  
  9. -- activation code
  10.     if IsQuestFlaggedCompleted(argv[2]) then
  11.       tooltip["message"] = ("Quest |cffffff00|Hquest:%d|h[%%s]|h|r flagged as completed."):format(argv[2])
  12.     else
  13.       tooltip["message"] = ("Quest |cffffff00|Hquest:%d|h[%%s]|h|r is not completed or not available to character."):format(argv[2])
  14.     end
  15.     DEFAULT_CHAT_FRAME:AddMessage("Retrieving quest information...")
  16.     tooltip:SetOwner(UIParent, "ANCHOR_NONE")
  17.     tooltip:SetScript("OnTooltipSetQuest", tooltip.GetQuestTitle)
  18.     tooltip:SetHyperlink("quest:" .. argv[2])

Tested on quest id:25323, it properly spit only one line. (Without unsetting OnTooltipSetQuest, it prints a second line, when quest item data is accessed, as semlar pointed out earlier.)

Phanx 07-26-13 01:18 AM

If you don't need the quest name immediately (eg. you can wait for OnTooltipSetQuest to happen) then that will work, though I'd suggest cleaning it up some. In no particular order:
  • Making a table in your slash command handler like that is pretty horrifying.
  • There's no need to set and un-set the script, since your code is the only code that's going to be setting hyperlinks to that tooltip. If you're worried about it, check the self.message value instead.
  • "self" isn't a very good thing to call the second arg passed to your slash handler, since that arg refers to the editbox the user typed the command in, and not to any "self" as used anywhere else in your addon.
  • You can cut the number of calls to string.format in half.
  • You should :Hide() your tooltip after getting the text.

Code:

local frame = CreateFrame("GameTooltip", "MyPrivateStuff_QuestInfoTooltipFrame", UIParent, "GameTooltipTemplate")

frame:SetScript("OnTooltipSetQuest", function(self)
        if not self.message then return end
        local title = MyPrivateStuff_QuestInfoTooltipFrameTextLeft1:GetText()
        self:Hide()
        DEFAULT_CHAT_FRAME:AddMessage(format(self.message, self.linkID, title))
        self.message, self.linkID = nil, nil
end

SLASH_MYPRIVATESTUFF1 = "/my"
SlashCmdList["MYPRIVATESTUFF"] = function(msg, editBox)
        local linkType, linkID = strsplit(" ", msg)
        if linkType == "quest" then
                if IsQuestFlaggedCompleted(linkID) then
                        frame.message = "Quest |cffffff00|Hquest:%d|h[%%s]|h|r flagged as completed."
                else
                        frame.message = "Quest |cffffff00|Hquest:%d|h[%%s]|h|r is not completed or not available to character."
                end
                frame.linkID = linkID
                DEFAULT_CHAT_FRAME:AddMessage("Retrieving quest information...")
                frame:SetOwner(UIParent, "ANCHOR_NONE")
                frame:SetHyperlink("quest:" .. linkID)
        else
                frame.message, frame.linkID = nil, nil
        end
end

Edit: You posted a revision while I was posting mine, but most of the above is (probably) still applicable. Also, either your new code should be throwing errors left and right because you're using argv in a scope where it's not defined, or that isn't your real code.

AnrDaemon 07-26-13 04:55 AM

Quote:

Originally Posted by Phanx (Post 281581)
If you don't need the quest name immediately (eg. you can wait for OnTooltipSetQuest to happen) then that will work, though I'd suggest cleaning it up some. In no particular order:

Yes, I largely don't need it immediately. Certainly not in the same frame - I have no intention to get WoW stuck on every other window opening.
Though, that previous example with metatable will be a little better for when I need to store and handle a list of quest names during a single session.

Quote:

* Making a table in your slash command handler like that is pretty horrifying
You refer to
Code:

local argv = { strsplit(" ", strtrim(msg)) }
?
Then how do you suggest I prepare it? I have no idea, how many words will be in parameters.

Quote:

* There's no need to set and un-set the script, since your code is the only code that's going to be setting hyperlinks to that tooltip. If you're worried about it, check the self.message value instead.
I'm unsetting it to prevent repeated access to handler, where I don't want it. also to save some processing. Of course, I could just pupulate some other variable with necessary data, and use it from some other function... Isn't that "a bit" too much of overhead?

Quote:

* "self" isn't a very good thing to call the second arg passed to your slash handler, since that arg refers to the editbox the user typed the command in, and not to any "self" as used anywhere else in your addon.
"self" Is always the first argument passed to class function. Where do you see it as second?

Quote:

* You can cut the number of calls to string.format in half.
Yes, I can. I just left it this way to reduce amount of unrelated stuff referenced in far-reaching places.

Quote:

* You should :Hide() your tooltip after getting the text.
I never Show() it in first place. However, I can set OnShow = Hide, if you insist.

Quote:

Edit: You posted a revision while I was posting mine, but most of the above is (probably) still applicable. Also, either your new code should be throwing errors left and right because you're using argv in a scope where it's not defined, or that isn't your real code.
That is a part of real code, a part of real slashcommand handler. (There's lots more of unrelated stuff handled, I just extracted the relevant block for demonstration.)

Phanx 07-26-13 10:04 PM

Quote:

Originally Posted by AnrDaemon (Post 281587)
You refer to
Code:

local argv = { strsplit(" ", strtrim(msg)) }
?
Then how do you suggest I prepare it? I have no idea, how many words will be in parameters.

According to the code you posted, your code only supports two parameters, and the first one must always be "quest". If your code actually supports other commands, you'll have to post your real code for a real example of how to do it without making tables left and right, but it's definitely possible, just the way I showed you in the code I posted.

Quote:

Originally Posted by AnrDaemon (Post 281587)
"self" Is always the first argument passed to class function. Where do you see it as second?

In the code you posted, you named the second variable received by your slash command handler function "self".

Quote:

Originally Posted by AnrDaemon (Post 281587)
I never Show() it in first place. However, I can set OnShow = Hide, if you insist.

Calling SetHyperlink on the tooltip automatically shows it. You just don't see it appear because you didn't give it a position, so it's appearing in a nonexistent location. Just call :Hide() on it, which is the proper method of "cleaning up" a tooltip after you've read it.

Quote:

Originally Posted by AnrDaemon (Post 281587)
That is a part of real code, a part of real slashcommand handler. (There's lots more of unrelated stuff handled, I just extracted the relevant block for demonstration.)

Posting random parts of your code is nothing but a huge waste of time for anyone who tries to help you. If you want help, post your entire, actual code. We aren't mind readers. We can't magically know that what you posted is only 10% of your code, or what is in the other 90% of your code. Clearly you do not actually want help, so I'm done trying to help you. Maybe someone else has more patience for your time-wasting than I do. Good luck.

AnrDaemon 07-27-13 12:08 AM

Quote:

Originally Posted by Phanx (Post 281618)
According to the code you posted, your code only supports two parameters, and the first one must always be "quest". If your code actually supports other commands, you'll have to post your real code for a real example of how to do it without making tables left and right, but it's definitely possible, just the way I showed you in the code I posted.

Yeah, sorry for confusion.

Quote:

In the code you posted, you named the second variable received by your slash command handler function "self".
Aww, blind my eyes. Found it. That's really wrong way to handle things, indeed.

Quote:

Calling SetHyperlink on the tooltip automatically shows it.
I was afraid of that, on a second thought. Fixed now.

Quote:

Posting random parts of your code is nothing but a huge waste of time for anyone who tries to help you. If you want help, post your entire, actual code. We aren't mind readers. We can't magically know that what you posted is only 10% of your code, or what is in the other 90% of your code. Clearly you do not actually want help, so I'm done trying to help you. Maybe someone else has more patience for your time-wasting than I do. Good luck.
Now, that's the kind of attitude, which I like.
Yes, I don't need any more help, than you've provided already. Thank you.
Even less I need to be spoon-fed with complete solutions. I'm not brain-damaged, and I still capable of producing my own solutions provided enough strarting information. Which you did. Thank you once more.
You even helped me to realize subtle mistakes in my code, which I did not know, and pointed out a major oversight. Great thank you for that.
You was of a very big help. Thank you once more.

ckaotik 07-27-13 12:41 AM

And this is why I love WoWInterface's developer community. Never thought of using the almighty SetTooltipHyperlink("quest:"..questID) treatment.
Here's another thank you!

Phanx 07-27-13 09:06 PM

Quote:

Originally Posted by AnrDaemon (Post 281625)
Even less I need to be spoon-fed with complete solutions. I'm not brain-damaged, and I still capable of producing my own solutions provided enough strarting information.

It's not about "spoon-feeding complete solutions". It's about the fact that I spent a good amount of time critiquing your code, but had you just posted your whole code in the first place, half of those critiques would have been invalid or significantly different. You wasted your time cherry-picking some parts of your code to post, and I wasted my time critiquing fake code and trying to explain to you why things were problems, when they weren't actually problems in your real code. It would have been faster for you, and less annoying for everyone, to just post your whole file and say "please don't solve the problem, just give me a hint!"

AnrDaemon 08-04-13 11:50 AM

Sorry, but your incrimination makes little sense. I posted my code, when it was written. I didn't held it back on purpose, or anything of that kind.

McRoell 07-03-18 12:18 AM

Sorry for pulling this thread out of hibernation, but I've encountered a problem with that "frame:SetScript" part(I guess) I'm not able to solve.

Quote:

Originally Posted by Phanx (Post 281581)
Code:

local frame = CreateFrame("GameTooltip", "MyPrivateStuff_QuestInfoTooltipFrame", UIParent, "GameTooltipTemplate")

frame:SetScript("OnTooltipSetQuest", function(self)
        if not self.message then return end
        local title = MyPrivateStuff_QuestInfoTooltipFrameTextLeft1:GetText()
        self:Hide()
        DEFAULT_CHAT_FRAME:AddMessage(format(self.message, self.linkID, title))
        self.message, self.linkID = nil, nil
end


I've used the complete code provided by Phanx 1:1 into my LUA-Script. Every time on Login (or Reload) I receive an Error regarding a missing ")" for closing purpose - details below.

As far as I (as a newbie) understand the code, the error should refer to the "frame:SetScript" statement, but I'm not sure on that and much less how to solve that.

Error Message
Code:

Message: Interface\AddOns\McR_Queststat\mcr_queststat.lua:28: ')' expected (to close '(' at line 20) near 'SLASH_MYPRIVATESTUFF1'
Time: Tue Jul  3 07:53:23 2018
Count: 1
Stack: Interface\AddOns\McR_Queststat\mcr_queststat.lua:28: ')' expected (to close '(' at line 20) near 'SLASH_MYPRIVATESTUFF1'
[C]: ?

Locals:

TIA

McRoell

Fizzlemizz 07-03-18 12:50 AM

Code:

frame:SetScript("OnTooltipSetQuest", function(self)
        if not self.message then return end
        local title = MyPrivateStuff_QuestInfoTooltipFrameTextLeft1:GetText()
        self:Hide()
        DEFAULT_CHAT_FRAME:AddMessage(format(self.message, self.linkID, title))
        self.message, self.linkID = nil, nil
end)

Phanx left off the final ) after the last end.

AnrDaemon 07-03-18 05:52 AM

I strongly suggest an editor capable of structure highlighting, not just keywords.

McRoell 07-03-18 11:04 PM

Quote:

Originally Posted by Fizzlemizz (Post 328531)
[code]Phanx left off the final ) after the last end.

Thank you.
I slightly guessed it but had an other issue with that code - usage - which was spoiling my efforts. Thanks to your confirmation I'm all-clear now.

McRoell

Nikita S. Doroshenko 04-27-20 09:46 AM

Maybe someone knows if it's possible somehow to obtain localized string on different installed languages for quest titles, descriptions, unit titles.
I think it's possible to do with Blizzard API https://develop.battle.net/documenta...game-data-apis
But I wonder if it's possible for example GET quest Title, Description for es_ES, and de_DE ingame?

I have an idea of making an addon that will help players to learn a foreign language, but I'm not sure what will be the best way to get multiple localization data at the same time. And make addon easy to maintain in case of new content and updates.

Ketho 04-27-20 10:21 AM

Quote:

Originally Posted by Nikita S. Doroshenko (Post 335770)
But I wonder if it's possible for example GET quest Title, Description for es_ES, and de_DE ingame?


I don't think that's possible in-game. You'd only get the info for your current locale


All times are GMT -6. The time now is 03:10 AM.

vBulletin © 2024, Jelsoft Enterprises Ltd
© 2004 - 2022 MMOUI