Conversation Key Matches wrong thing?
ender
21 Nov 2011, 04:06Okay, I've got a situation where I have different colored key cards the player is supposed to find ... and part of how I want them to find them (and figure out what they do) is to ask NPC's .... but I've run into a snag with the conversation system.
If I've got this set up using the built in 'ASK' assigned to an object "Marcus":
KEY : Red Keycard - SCRIPT: (Print Message) "I think I saw the red keycard in the engine room."
KEY : Blue Keycard - SCRIPT: (Print Message) "Oh, I've got that right here."
If the player goes to marcus and does 'Ask Marcus About Red Keycard' .... the Quest 5 engine will match and run the script for the BLUE KEYCARD ... probably because its matching the last instance of 'keycard' ...
Even if its just looking at the 'keys' and trying match them ... red keycard should match the players input better than blue keycard ... I'd expect the system to get confused if they player just said 'ask about keycard' ...
Is there something I can do to get it to match better?
My only thought is to set up an ask for 'keycard' ... and then use a menu to say 'which keycard? the blue one or the red one?" .... but that seems kind of clunky to me ... and since I expect to end up with several similar kinds of keys ... could get a little complicated to manage.
Idealy ... I'd like to find some way to make the built in quest 'ask about' system work.
Thanks.
If I've got this set up using the built in 'ASK' assigned to an object "Marcus":
KEY : Red Keycard - SCRIPT: (Print Message) "I think I saw the red keycard in the engine room."
KEY : Blue Keycard - SCRIPT: (Print Message) "Oh, I've got that right here."
If the player goes to marcus and does 'Ask Marcus About Red Keycard' .... the Quest 5 engine will match and run the script for the BLUE KEYCARD ... probably because its matching the last instance of 'keycard' ...
Even if its just looking at the 'keys' and trying match them ... red keycard should match the players input better than blue keycard ... I'd expect the system to get confused if they player just said 'ask about keycard' ...
Is there something I can do to get it to match better?
My only thought is to set up an ask for 'keycard' ... and then use a menu to say 'which keycard? the blue one or the red one?" .... but that seems kind of clunky to me ... and since I expect to end up with several similar kinds of keys ... could get a little complicated to manage.
Idealy ... I'd like to find some way to make the built in quest 'ask about' system work.
Thanks.

Pertex
21 Nov 2011, 08:01ender wrote:
KEY : Red Keycard - SCRIPT: (Print Message) "I think I saw the red keycard in the engine room."
KEY : Blue Keycard - SCRIPT: (Print Message) "Oh, I've got that right here."
This seems to be a bug.
Perhaps you could do the following:
KEY : Red - SCRIPT: (Print Message) "I think I saw the red keycard in the engine room."
KEY : Blue - SCRIPT: (Print Message) "Oh, I've got that right here."
KEY : Keycard- SCRIPT: (Print Message) "There are two keycards. Which do you mean?"
Alex
21 Nov 2011, 09:11Logged http://quest.codeplex.com/workitem/937
Hopefully Pertex's solution will work. The core library handling of ask/tell will ignore any words the player typed which don't match any topic keys.
Hopefully Pertex's solution will work. The core library handling of ask/tell will ignore any words the player typed which don't match any topic keys.
ender
21 Nov 2011, 21:02Thank you for the responses ... I think pertex's solution would work as long as there is never an instance of anything else 'red' ... i.e. red button ... which would work with small games, but could get tricky for larger games with lots of conversation oriented puzzles.
I think I remember someone saying we can overwrite built in functions ... so maybe I'll try to modify the ask/tell processor to improve its matching system to do what I want ...
Anyway ... thank you again.
I think I remember someone saying we can overwrite built in functions ... so maybe I'll try to modify the ask/tell processor to improve its matching system to do what I want ...
Anyway ... thank you again.
ender
21 Nov 2011, 21:57Okay ... I found the problem. It was actually pretty simple ... in the script you have a variable called 'maxstrength' which you set to 0 ....
Then you have a function GetKeywordsMatchStrength that compares the keywords and the user input and generates a strength ... as long as the GetKeywordsMatchStrength is greater than the maxstrength ... then it 'matches' ... unfortunately, you are never modifying the maxstrength variable ... it always stays as 0 .... so ANY match regardless of how good it is, will overwrite a previous match.
Here is my modified function:
This solves the main problem I brought up ... although pertex made me think of a different problem. General versus specific matching ... (keycard versus red keycard)
Since I used a >= ... if two items have the same strength, it will keep replacing the match until it gets to the last one in the series.
I.e.
Item One - Keys : Red Keycard
Item Two - Keys : Blue Keycard
Item Three - Keys : Keycard
if I just use the > operator, then if the users input is "ask about keycard" ... the output will match the first item in the list (so in this case : red keycard), and then ignore any other match ... but thats not really what we want.
We want it to match the generic 'keycard' item ... so by using >=, and putting Keycard as the last item, then if the user just inputs ask about keycard ... the system will run the 'keycard' script.
Its really half a dozen of one/six of the other ... either way it forces you to modify the position of what you want to match 'in general' versus 'in specific'.
This is not really ideal, but it will do for now. I will continue to tinker with this and if I get a better solution together, I'll post it.
Then you have a function GetKeywordsMatchStrength that compares the keywords and the user input and generates a strength ... as long as the GetKeywordsMatchStrength is greater than the maxstrength ... then it 'matches' ... unfortunately, you are never modifying the maxstrength variable ... it always stays as 0 .... so ANY match regardless of how good it is, will overwrite a previous match.
Here is my modified function:
<function name="DoAskTell" parameters="object, text, property, defaultscript, defaulttemplate"><![CDATA[
handled = false
maxstrength = 0
match = null
text = LCase(text)
if (typeof(object, property) = "scriptdictionary") {
dictionary = GetAttribute(object, property)
foreach (keywords, dictionary) {
if (GetKeywordsMatchStrength(LCase(keywords), text) >= maxstrength) {
match = ScriptDictionaryItem(dictionary, keywords)
maxstrength = GetKeywordsMatchStrength(LCase(keywords), text)
}
}
if (match <> null) {
invoke (match)
handled = true
}
}
if (not handled) {
if (HasScript(object, defaultscript)) {
do (object, defaultscript)
}
else {
msg (DynamicTemplate(defaulttemplate, object))
}
}
]]></function>
This solves the main problem I brought up ... although pertex made me think of a different problem. General versus specific matching ... (keycard versus red keycard)
Since I used a >= ... if two items have the same strength, it will keep replacing the match until it gets to the last one in the series.
I.e.
Item One - Keys : Red Keycard
Item Two - Keys : Blue Keycard
Item Three - Keys : Keycard
if I just use the > operator, then if the users input is "ask about keycard" ... the output will match the first item in the list (so in this case : red keycard), and then ignore any other match ... but thats not really what we want.
We want it to match the generic 'keycard' item ... so by using >=, and putting Keycard as the last item, then if the user just inputs ask about keycard ... the system will run the 'keycard' script.
Its really half a dozen of one/six of the other ... either way it forces you to modify the position of what you want to match 'in general' versus 'in specific'.
This is not really ideal, but it will do for now. I will continue to tinker with this and if I get a better solution together, I'll post it.
Alex
22 Nov 2011, 09:39Thanks! I have checked in that fix (slightly updated so it doesn't call GetKeywordsMatchStrength twice).