def move_by(self, delta_x, delta_y): # guard against anyone but the main program or _move_to calling me callername.caller_name_match(r"__main__|\._move_to$", abort = True, debug = agentsim.debug.get(256)) if self._move_limit is not None: delta_d = (delta_x * delta_x + delta_y * delta_y) ** 0.5 if delta_d > self._move_limit: delta_x = delta_x * self._move_limit / delta_d delta_y = delta_y * self._move_limit / delta_d # Don't allow you to move onto another person. This means that if # you are already on a person, you have to jump off by making a big # move. no_collision = True; # only collide with someone present for p in Person.get_all_present_instances(): # would we collide with p? if self.is_near_after_move(p, delta_x, delta_y): if agentsim.debug.get(16): print("MoveEnhanced.move_by", self.get_name(), "would collide with", p.get_name(), delta_x, delta_y) no_collision = False break # make the move if no collision if no_collision: if agentsim.debug.get(16): print("MoveEnhanced.move_by", self.get_name(), "moving by", delta_x, delta_y) super(MoveEnhanced, self).move_by(delta_x, delta_y)
def compute_next_move(self): overlapping = False # check if we're overlapping with anyone and move off everyone = Person.get_all_present_instances() if len(everyone) > 1: nearest = min( # make pairs of (person, distance from self to person) [ (p, self.distances_to(p) ) for p in everyone if p.get_id() != self.get_id()] , # and sort by edge-to-edge distance key=(lambda x: x[1][3]) ) (d, delta_x, delta_y, d_edge_edge) = nearest[1] if d > 0 and d_edge_edge < 0: # Means we're overlapping with the nearest person # Let's move directly away from them and hope they'll # do the same overlapping = True # move in exactly the opposite direction of person # with which we're overlapping but move maximum # distance allowed # We'll still be stuck if move_limit isn't far enough # to fix overlap move_limit = self.get_move_limit() delta_x = -delta_x * (move_limit/d) delta_y = -delta_y * (move_limit/d) # if we have a pending zombie alert, act on that if we're not overlapping if not overlapping and self._zombie_alert_args is not None: (x, y) = self._zombie_alert_args delta_x = x - self.get_xpos() delta_y = y - self.get_ypos() # clear the alert self._zombie_alert_args = None return (delta_x, delta_y)