+import xml.etree.cElementTree as ET
+import textwrap
+
+# function to run through an interactive dialogue and return the response ID
+def dialogue_play (screen, bgscreen, npc, responder,
+ marginleft=0, margintop=0, marginright=0, marginbottom=0):
+
+ # first check if NPC has a dialogue at all
+ if len (npc.dialogues) == 0 or npc.currentdialog >= len (npc.dialogues):
+ return None
+
+ # get the conversation as a dictionary
+ convtree = xml_to_dict (npc.dialogues[npc.currentdialog])
+
+ scrwidth = screen.get_width ()
+ scrheight = screen.get_height ()
+ bgwidth = bgscreen.get_width ()
+ bgheight = bgscreen.get_height ()
+ leftedge = scrwidth/2 - bgwidth/2
+ topedge = scrheight/2 - bgheight/2
+
+ # now initiate the conversation
+ dlg_id = "1"
+ while 1:
+ screen.blit (bgscreen, (leftedge, topedge))
+ if npc.portrait is not None:
+ screen.blit (npc.portrait, (leftedge, topedge))
+
+ # get the lines to display wrapped using textwrap module
+ lines = []
+ textnpc = textwrap.wrap (convtree[dlg_id][0], 40)
+ for text in textnpc:
+ lines.append ((10, 0, 0, 0, text))
+
+ put_lines (screen, lines,
+ pygame.Rect(leftedge+marginleft, topedge+margintop,
+ bgwidth-marginleft-marginright, bgheight-margintop-marginbottom))
+ pygame.display.update ()
+
+ for event in pygame.event.get ():
+ if event.type == pygame.QUIT:
+ sys.exit (0)
+
+# function to parse a conversation XML into a python dictionary
+def xml_to_dict (file):
+ # parse the dialogue XML file
+ dlgtree = ET.parse (file)
+ # get the root element
+ conversation = dlgtree.getroot ()
+
+ # build the conversation tree as a dictionary
+ convtree = dict ()
+ for dlg in conversation.findall ("dialogue"):
+ id = dlg.get ("id")
+ convtree[id] = []
+ convtree[id].append (dlg.find ("speech").text)
+ for resp in dlg.findall ("response"):
+ convtree[id].append ((resp.text, resp.get ("id"), resp.get ("nextdialogue")))
+
+ return convtree
+