mod_a = {"Method" : {"name" : SocialNode.move_player_to_node, "self" : {"ref" : "Player"}, "args" : [{"ref" : "Recipient"}]}} Move_2 = [mod_a] # Kill Victim mod_1 = {"Method" : {"name" : SocialNode.murder, "self" : {"ref" : "Recipient"}, "args" : [{"ref" : "Player"}]}} mod_2 = {"Attribute" : {"name" : {"ref" : "Recipient"}, "key" : "alive", "value" : False}} mod_3 = {"Method" : {"name" : SocialNode.set_other_nodes_relations, "self" : {"ref" : "Recipient"}, "args" : [["Friends", "Loves"], "Hates", {"ref" : "Invoker"}, "MurderBlackmailer_of_"]}} mod_4 = {"Method" : {"name" : SocialNode.set_other_nodes_relations, "self" : {"ref" : "Recipient"}, "args" : [["Hates", "Enemies"], "Friends", {"ref" : "Invoker"}, "MurderBlackmailer_of_"]}} Kill_Modification = [mod_1, mod_2, mod_3, mod_4] #---------------------------------- # Story Results #---------------------------------- One = StoryNode("MurderBlackmailer_Request_from_Invoker", {"Node_Type" : "Info"}, A) One.set_modification(Move_1) Two = StoryNode("Go_To_Victim", {"Node_Type" : "Go_To"}, B) Two.set_modification(Move_2) Three = StoryNode("Kill_Victim", {"Node_Type" : "MurderBlackmailer"}, B) Three.set_modification(Kill_Modification) Four = StoryNode("Return_to_Invoker", {"Node_Type" : "Return"}, A) Four.set_modification(Move_1) MurderBlackmailer_Story = StoryGraph("MurderBlackmailer_Story", [One, Two, Three, Four]) MurderBlackmailer_Story.connect(One, {}, Two) MurderBlackmailer_Story.connect(Two, {}, Three) MurderBlackmailer_Story.connect(Three, {}, Four) MurderBlackmailer_Rule = RewriteRule(None, MurderBlackmailer, MurderBlackmailer_Story, None, "Murder_Blackmailer")
def readGraph(self): tree = ET.parse(self._filename) root = tree.getroot() #Get our graph name graph_name = root.attrib.get('name') #Process the nodes node_list = [] for node in root.iter('node'): story_node_name = node.attrib['name'] node_attributes = {} #Get the target node_target = node.find('target').text #Get the node type node_attributes['Node_Type'] = node.find('nodetype').text #Get the attributes for attribute in node.findall('attr'): attribute_type = attribute.attrib.get('type') attribute_name = attribute.attrib.get('name') attribute_value = attribute.find('value').text if attribute_type == 'bool': node_attributes[attribute_name] = ( attribute_value == "True") elif attribute_type == 'int': node_attributes[attribute_name] = int(attribute_value) elif attribute_type == 'float': node_attributes[attribute_name] = float(attribute_value) else: node_attributes[attribute_name] = attribute_value new_node = StoryNode(story_node_name, node_attributes, self._graph.get_node_from_name(node_target)) if not node.attrib['modification'] == 'None': modification_filename = self._path + "Modifications/" + node.attrib[ 'modification'] modification_reader = XMLModificationReader( modification_filename) modification = modification_reader.readModification() new_node.set_modification(modification) node_list.append(new_node) #Create the Return Graph returnGraph = StoryGraph(graph_name, node_list) #Begin Making the connections for connection in root.iter('connection'): connect_from = connection.attrib.get('from') from_node = returnGraph.get_node_from_name(connect_from) connect_to = connection.attrib.get('to') to_node = returnGraph.get_node_from_name(connect_to) relation = connection.find('relation').attrib if relation.keys()[0] == "none": relation = {} returnGraph.connect(from_node, relation, to_node) return returnGraph
def readGraph(self): tree = ET.parse(self._filename) root = tree.getroot() #Get our graph name graph_name = root.attrib.get('name') #Process the nodes node_list = [] for node in root.iter('node'): story_node_name = node.attrib['name'] node_attributes = {} #Get the target node_target = node.find('target').text #Get the node type node_attributes['Node_Type'] = node.find('nodetype').text #Get the attributes for attribute in node.findall('attr'): attribute_type = attribute.attrib.get('type') attribute_name = attribute.attrib.get('name') attribute_value = attribute.find('value').text if attribute_type == 'bool': node_attributes[attribute_name] = (attribute_value == "True") elif attribute_type == 'int': node_attributes[attribute_name] = int(attribute_value) elif attribute_type == 'float': node_attributes[attribute_name] = float(attribute_value) else: node_attributes[attribute_name] = attribute_value new_node = StoryNode(story_node_name, node_attributes, self._graph.get_node_from_name(node_target)) if not node.attrib['modification'] == 'None': modification_filename = self._path + "Modifications/" + node.attrib['modification'] modification_reader = XMLModificationReader(modification_filename) modification = modification_reader.readModification() new_node.set_modification(modification) node_list.append(new_node) #Create the Return Graph returnGraph = StoryGraph(graph_name, node_list) #Begin Making the connections for connection in root.iter('connection'): connect_from = connection.attrib.get('from') from_node = returnGraph.get_node_from_name(connect_from) connect_to = connection.attrib.get('to') to_node= returnGraph.get_node_from_name(connect_to) relation = connection.find('relation').attrib if relation.keys()[0] == "none": relation = {} returnGraph.connect(from_node, relation, to_node) return returnGraph
#---------------------------------- # Social Condition #---------------------------------- Monster = SocialNode("Monster", {"alive": True}) Recipient = SocialNode("Recipient", {"alive" : True}) Ambush_Social_Condition = Graph("Stolen_Gift_Social_Condition", [Monster, Recipient]) Ambush_Social_Condition.connect(Monster, {"Hates" : "N/A"}, Recipient) #---------------------------------- # Social Modification #---------------------------------- #---------------------------------- # Story Condition #---------------------------------- Murder = StoryNode("Give_Gift", {"Node_Type" : "Give_Item"}, Recipient) Ambush_Story_Condition = StoryGraph("Stolen_Gift_Condition", [Murder]) #---------------------------------- # Story Outcome #---------------------------------- Spare = StoryNode("Stolen_Gift", {"Node_Type" : "Robbery", "Additional" : "Branched_Node"}, Monster) Foigh = StoryNode("Fight_For_Gift", {"Node_Type" : "Fight", "Additional" : "Branched_Node"}, Monster) Ambush_Story_Outcome = StoryGraph("Stolen_Gift_Story_Outcome", [Murder, Foigh, Spare]) Ambush_Story_Outcome.connect(Spare, {}, Foigh) Ambush_Rule = RewriteRule(Ambush_Story_Condition, Ambush_Social_Condition, Ambush_Story_Outcome, None, "Stolen_Gift", True) ##---------------------------------------------------- ## Ambush Skeleton ##---------------------------------------------------- # ##----------------------------------
def initialize_narrative(self): #----------------------------------- # Create the Beginning Narrative Format #----------------------------------- #Create the starting node and ending node start_node = StoryNode("Start_Quest", {"Node_Type": "Start"}, "N/A") end_node = StoryNode("End_Quest", {"Node_Type": "End"}, "N/A") #Initialize our narrative self._narrative = StoryGraph("New_Quest", [start_node, end_node]) self._narrative.initialize() print "Creating Initial Narrative" #----------------------------------- #We will go throughout all our rules and find matching results #----------------------------------- print "Searching for Possible Narrative Rules..." matching_rules = self.get_possible_rules(self._story_init_rules, self._social_graph) print "Found " + str(len(matching_rules)) + " possible rules" if len(matching_rules) <= 0: print "ERROR - No Matching Rules found, No more stories may be created" return False #Rules for picking the matching narrative #At the moment it is a random choice if self._verbose: print "Found the Following Matching Initialization Rules: " for rule in matching_rules: print "\t" + rule[1].get_name() resultant = choice(matching_rules) resulting_rule = resultant[1] #Rules for picking the matching group #At the moment it is a random choice resulting_group = choice(resultant[0]) #----------------------------------- #Now we set the cast for our narrative #----------------------------------- cast = {} #The cast is stored as a dictionary where the name in the condition narrative #is the key for the node it relates to for i in range(len(resulting_group)): cast[resulting_rule.get_social_condition().get_nodes() [i].get_name()] = resulting_group[i] #The player always participates in the narrative by default cast["Player"] = self._social_graph.get_player() self._narrative.set_cast(cast) #----------------------------------- #Now we set the preconditions for our narrative #----------------------------------- #We will convert the original social condition into a set of preconditions for i in range(len(resulting_group)): cur_node = resulting_rule.get_social_condition().get_nodes()[i] cur_attr = cur_node.get_attributes() #First we will create all of the attribute preconditions for key in cur_attr.keys(): condition = Condition(True) condition.set_first_object(resulting_group[i]) condition.set_key(key) condition.set_value(cur_attr[key]) self._narrative.add_precondition(condition) #Following this, we will create all of the edge preconditions for edge in cur_node.get_outgoing_edges(): condition = Condition(False) condition.set_first_object(resulting_group[i]) condition.set_second_object( cast[edge.get_to_node().get_name()]) condition.set_key(edge.get_name().keys()[0]) condition.set_value(edge.get_name()[edge.get_name().keys()[0]]) self._narrative.add_precondition(condition) #----------------------------------- #Now we construct our narrative skeleton using this modification #----------------------------------- story_modification = resulting_rule.get_story_modification() #Set up our nodes for node in story_modification.get_nodes(): #Get the index of the story node index = resulting_rule.get_social_condition().get_nodes().index( node.get_target()) #We can then pick the actual target from our group target = resulting_group[index] #Also, add the target as an attribute node.add_attribute("Target", target.get_name()) #And link the story node to this target node.set_linked_to_node(target) #Finally, add the node to the story self._narrative.add_node(node) #Edges are currently empty for narratives for edge in story_modification.get_edges(): self._narrative.add_edge(edge) return True