ID:265638
 
I was thinking for my NPCs in the game, a conversation could go as follows (all in say)

I am Flame Sage, the NPC is Bob.
Flame Sage: (Hey / Hello / Yo) Bob.
Bob: Hey Flame Sage, have you heard about the [dark alley] on that back road over there?
Flame Sage: What dark alley?
Bob: I heard it has a [secret weapon]!
Flame Sage: a secret weapon?
Bob: Yes! I also heard you like [pancakes]!
Flame Sage: Really? Pancakes?
Bob: Yes!
Flame Sage: Goodbye Bob
Bob: Bye Flame Sage.

I want the conversation to continue once the keyword in [ ] are spoken, to start (and end) the conversation, say Hello / Goodbye.

How would I have the NPC say the next line when that key word is spoken? How would I track what line of the conversation I am on?
Use findtext to see if the word was said, and use a numeric variable to keep track of what line you are on.
mob/NPC
var
conversation_progress = 0
list/conversation = (\
"hi" = "dark alley sentence",\
"dark alley" = "next sentence",\
"secret weapon" = "next sentence")
proc/listen(text)
if(findtext(text, "bye") && conversation_progress)
view(src) << "Bye!"
conversation_progress = 0
else
if(conversation_progress >= conversation.len)
//do whatever should happen here if you talk again once the conversation list is done
else
if(findtext(text, conversation[conversation_progress+1])
conversation_progress += 1
view(src) << conversation[conversation[conversation_progress]]

Something along those lines.
In response to Loduwijk
mob/mobile/NPC
icon='Base.dmi'
var
list/conversation = list(\
"hello" = "Hey, what's up?",\
"nothing" = "Oh, I see...",\
"secret weapon" = "next sentence")
proc/listen(text,var/mob/mobile/player/P)
if(findtext(text,lowertext("bye [src.name]")) && P.conversation_progress)
P<<"Goodbye!"
P.conversation_progress = 0
else
if(!P.conversation_progress)
if(P.conversation_progress >= conversation.len)P.tell(src,"[conversation[1]]")
else
if(findtext(text, conversation[P.conversation_progress+1]))
P.conversation_progress++
P.tell(conversation[P.conversation_progress],src,P)
else P<<"You are currently talking to another NPC."
bob/
name="Bobby"
mob/mobile/player/proc/tell(MSG as text,var/mob/mobile/Teller,var/mob/mobile/Reciever)
Reciever<<"[Teller] says [MSG]"


When I say hello to bobby, I simply get back hello, it doesn't actually speak the text it's supposed to.

Also; how would I go about generating the list whenever the user talks to them?

Example; Hello Flame Sage, how are you?
In response to Flame Sage
im not a perfessional coder, but i do know when thats compleate that would be AWSOME, also would the keywords be in the []? or will there be some sort of hint on the keywords?
In response to Flame Sage
Hm, I think the reason why you are getting "hello" back is because you messed up your tell()..

The first instance I saw it says:
P.tell(src,"[conversation[1]]")


I assume that it goes like this: P receives the message, src is the NPC name (eg NPC: msg) and the quote after src is the message


A bit down, you do tell() like this:
P.tell(conversation[P.conversation_progress],src,P)


Actually, I doubt this may be the case but you might want to look into that anyways.
-------------

Also, you are doing this:
findtext(text, conversation[P.conversation_progress+1]))


I do not understand what you were trying to do with this, because this is what is going to happen (assuming that prograss is at 0):
findtext("hello","Hey, what's up")
.. This will always return false because what you are doing here is LOOKING FOR "Hey, what's up" IN "hello", I think you wanted
if(conversation[P.conversation_progress+1]==conversation[text])
or something similar >_>


- GhostAnime
In response to GhostAnime
That first part, that was my bad, you were right.

But the second part is wrong, whenever I try to do +1 to the conversation, it gives me the second keyword, (Because it's an associative list), how would I have it output the sentence?
In response to Flame Sage
Oops, my bad about the second one, I keep forgetting about that.

From the top of my head, you can do this:
//old --> conversation[P.conversation_progress]
conversation[conversation[P.conversation_progress]]// after the increase of the progress


What the very first set of list[#] does is return the first value (let's call this the outer value in the example list=list("outer"="inner")). So when you do list[list[#]], you'll get the inner value because:

list[list[#]] => list[list[1]] => list["outer"] => "inner"


Er, hope I got that right.

- GhostAnime
In response to VolksBlade
The keywords would be in brackets.

This is much similar to EverQuest's NPC dialogue system.
In response to Silent Sage
oic, thats a great idea, i would kill to have that type of a system in my games
In response to GhostAnime
Yes, I did make a bit of a mistake on that part, sorry about that.

In an associative list, if you want to access the value associated with the value at index n, you do have to do list[list[n]].
In response to Loduwijk
That's sooo restricted. Why not create a word matrix sort of thing? I started working on something like that. I tried making it so the NPC has a certain rep with you and depending on your rep with them, when you say "Hello" to them, they could say "Hey!", or something to that effect(three different phrases for each rep category) or they could say "Piss off."

Something like this...

var/global/list/wordmatrix[]=list(\
"Greetings"=list("hello","how are you","hi","hey","good mornin","good afternoon","good evening","good night","greetings","salutations","sup","whats up","ey"),\
"Goodbye"=list("bye","later","see ya","good-bye","goodbye","good bye","good night","farewell","cya","c u","see u","see you"),\
"Who are you"=list("who are you","what's your name","wat's your name","wats your name","whats your name","who're you"),\
"What do you do"=list("whats your job","what's your job","wat's your job","wats your job","what do you do","what's your occupation","wat's your occupation","whats your occupation","wats your occupation"),\
"Good"=list("good","great","well","fine","awesome","ok","alright"),\
"Not good"=list("not good","not great","not well","not fine","not awesome","not ok","not alright","bad","miserable","horrible","awful"),\
"Thanks"=list("thanks","thx","thnx","thank you","i appreciate","ty"),\
"Me"=list("me","i","myself"),\
"Compliments"=list("great work","excellent","good work","nice job","good job","great job","nice work"),\
"Stop"=list("stop","don't move","dont move","cease"),\
"Come"=list("come","get over here","get here","follow","i need you"),\
"Insults"=list(),\
"Perv"=list()//editted out for obvious reasons.
)


I made this a long time ago and I made it to be similar to Dream Forge's methods, so you need to target an NPC and if you say their name it auto-targets them and initiates a conversation.

    verb
Talk(t as text)
if(t)
for(var/mob/M in view())
M<<"[usr] says : [t]"
if(findtext(t,M.name))
usr.target=M
M.overlays+=new/obj/target
if(usr.target==M)
M.Convo(usr,t)
else
return
proc
Convo(mob/M,msg)
msg="[lowertext(msg)]"
if(src.rep["[M.name]"])
for(var/v in wordmatrix["Perv"])
if(findtext(msg,v))
sleep(25)
if(src.rep["[M.name]"]>=75)
view(src)<<pick("[src] says : I thought we were friends!!!",\
"[src] says : You were just after sex!",\
"[src] says : You disgust me.")
src.rep["[M.name]"]-=rand(0,3)
else if(src.rep["[M.name]"]>=50)
view(src)<<pick("[src] says : Ungh!",\
"[src] says : Get away from me.",\
"[src] says : Don't make me get the authorities!")
src.rep["[M.name]"]-=rand(1,4)
else if(src.rep["[M.name]"]>=25)
view(src)<<pick("[src] says : Back off!!!",\
"[src] says : You're such a loser!",\
"[src] says : You're disgusting...")
src.rep["[M.name]"]-=rand(1,5)
else if(src.rep["[M.name]"]>=0)
view(src)<<pick("[src] says : You pig!",\
"[src] says : You sicken me.",\
"[src] says : Vile.")
src.rep["[M.name]"]-=rand(0,5)
return


The Convo() proc isn't shown completely as it's too long, but you get the point.

-Exophus