def goto_nearest_boost(self, only_small=False): if self.is_clear(): self.send_quick_chat(QuickChats.CHAT_TEAM_ONLY, QuickChats.Information_NeedBoost) if not only_small: large_boosts = ( boost for boost in self.boosts if boost.large and boost.active and self.friend_goal.location.y - boost.location.y >= 0) closest = peek_generator(large_boosts) if closest is not None: closest_distance = closest.location.flat_dist( self.friend_goal.location) for item in large_boosts: item_distance = item.location.flat_dist( self.friend_goal.location) if item_distance is closest_distance: if item.location.flat_dist( self.me.location ) < closest.location.flat_dist(self.me.location): closest = item closest_distance = item_distance elif item_distance < closest_distance: closest = item closest_distance = item_distance self.push(goto_boost(closest, self.ball.location)) small_boosts = (boost for boost in self.boosts if not boost.large and boost.active) closest = peek_generator(small_boosts) if closest is not None: closest_distance = closest.location.flat_dist(self.me.location) for item in small_boosts: item_distance = item.location.flat_dist(self.me.location) if item_distance < closest_distance and item.location.flat_dist( self.friend_goal.location ) < self.ball_to_goal - 750: closest = item closest_distance = item_distance if closest.location.flat_dist( self.friend_goal.location) < self.ball_to_goal - 750: self.push(goto_boost(closest, self.ball.location))
def goto_nearest_boost(self): # Get a list of all of the large, active boosts boosts = tuple(boost for boost in self.boosts if boost.active and boost.large) # if there's at least one large and active boost if len(boosts) > 0: # Get the closest boost closest_boost = min( boosts, key=lambda boost: boost.location.dist(self.me.location)) # Goto the nearest boost self.push(routines.goto_boost(closest_boost))
def run(self): # NOTE This method is ran every tick # If the kickoff isn't done if not self.kickoff_done: # If the stack is clear if self.is_clear(): # Push a generic kickoff to the stack # TODO make kickoff routines for each of the 5 kickoffs positions self.push(routines.generic_kickoff()) # we don't want to do anything else during our kickoff return # If the stack if clear and we're in the air if self.is_clear() and self.me.airborne: # Recover - This routine supports floor, wall, and ceiling recoveries, as well as recovering towards a target self.push(routines.recovery()) # we've made our decision and we don't want to run anything else return # If we have less than 36 boost # TODO this bot will go for boost no matter what - this is AWFUL, especially in a 1v1! if self.me.boost < 36: # If the stack is clear if self.is_clear(): # Get a list of all of the large, active boosts boosts = tuple(boost for boost in self.boosts if boost.active and boost.large) # if there's at least one large and active boost if len(boosts) > 0: # Get the closest boost closest_boost = min(boosts, key=lambda boost: boost.location.dist( self.me.location)) # Goto the nearest boost self.push(routines.goto_boost(closest_boost)) # we've made our decision and we don't want to run anything else if not self.is_clear(): return # if the stack is clear, then run the following - otherwise, if the stack isn't empty, then look for a shot every 4th tick while the other routine is running if self.is_clear() or self.odd_tick == 0: shot = None # TODO we might miss the net, even when using a target - make a pair of targets that are small than the goal so we have a better chance of scoring! # If the ball is on the enemy's side of the field, or slightly on our side if self.ball.location.y * utils.side(self.team) < 640: # Find a shot, on target - double_jump, jump_shot, and ground_shot are automatically disabled if we're airborne shot = tools.find_shot(self, self.foe_goal_shot) # TODO Using an anti-target here could be cool - do to this, pass in a target tuple that's (right_target, left_target) (instead of (left, right)) into tools.find_shot (NOT tools.find_any_shot) # TODO When possible, we might want to take a little bit more time to shot the ball anywhere in the opponent's end - this target should probably be REALLY LONG AND HIGH! # If we're behind the ball and we couldn't find a shot on target if shot is None and self.ball.location.y * utils.side( self.team) < self.me.location.y * utils.side(self.team): # Find a shot, but without a target - double_jump, jump_shot, and ground_shot are automatically disabled if we're airborne shot = tools.find_any_shot(self) # If we found a shot if shot is not None: # If the stack is clear if self.is_clear(): # Shoot self.push(shot) # If the stack isn't clear else: # Get the current shot's name (ex jump_shot, double_jump, ground_shot or Aerial) as a string current_shot_name = self.stack[0].__class__.__name__ # Get the new shot's name as a string new_shot_name = shot.__class__.__name__ # If the shots are the same type if new_shot_name is current_shot_name: # Update the existing shot with the new information self.stack[0].update(shot) # If the shots are of different types else: # Clear the stack self.clear() # Shoot self.push(shot) # we've made our decision and we don't want to run anything else return # TODO this setup is far from ideal - a custom shadow/retreat routine is probably best for the bot... # Make sure to put custom routines in a separate file from VirxERLU routines, so you can easily update VirxERLU to newer versions. # If the stack is still clear if self.is_clear(): # If ball is in our half if self.ball.location.y * utils.side(self.team) > 640: retreat_routine = routines.retreat() # Check if the retreat routine is viable if retreat_routine.is_viable(self): # Retreat back to the net self.push(retreat_routine) # If the ball isn't in our half else: shadow_routine = routines.shadow() # Check if the shadow routine is viable if shadow_routine.is_viable(self): # Shadow self.push(shadow_routine)
def goto_nearest_boost(self, only_small=False, clear_on_valid=False): if self.is_clear() or clear_on_valid: self.send_quick_chat(QuickChats.CHAT_TEAM_ONLY, QuickChats.Information_NeedBoost) ball_slice = self.ball_prediction_struct.slices[min( round(self.future_ball_location_slice * 1.1), 6)].physics ball = Vector(ball_slice.location.x, ball_slice.location.y, ball_slice.location.z) ball_v = Vector(ball_slice.velocity.x, ball_slice.velocity.y, ball_slice.velocity.z) ball_y = ball.y * side(self.team) if not only_small: if len(self.friends) > 0: large_boosts = ( boost for boost in self.boosts if boost.large and boost.active and ( (self.playstyle is self.playstyles.Offensive and boost.location.y * side(self.team) < -3000) or (self.playstyle is self.playstyles.Neutral and boost.location.y * side(self.team) > -100) or (self.playstyle is self.playstyles.Defensive and boost.location.y * side(self.team) > 3000))) else: if (ball_v.angle2D(self.foe_goal.location - ball) < 1 and ball_y > 0) or abs( ball.x) < 900 or self.predictions['own_goal']: large_boosts = None else: ball_x = sign(ball.x) large_boosts = ( boost for boost in self.boosts if boost.large and boost.active and ( boost.location.y * side(self.team) > ball_y - 50) and sign(boost.location.x) == ball_x) if large_boosts is not None: closest = peek_generator(large_boosts) if closest is not None: closest_distance = closest.location.flat_dist( self.me.location) for item in large_boosts: item_distance = item.location.flat_dist( self.me.location) if item_distance is closest_distance: if item.location.flat_dist( self.me.location ) < closest.location.flat_dist( self.me.location): closest = item closest_distance = item_distance elif item_distance < closest_distance: closest = item closest_distance = item_distance if clear_on_valid: self.clear() self.push(goto_boost(closest)) return True if (ball_v.angle2D(self.foe_goal.location - ball) < 1 and ball_y > 0) or self.predictions['own_goal']: return False ball_x = sign(ball.x) small_boosts = (boost for boost in self.boosts if not boost.large and boost.active and boost.location.y * side(self.team) > ball_y - 50 and sign(boost.location.x) == ball_x) closest = peek_generator(small_boosts) if closest is not None: closest_distance = closest.location.flat_dist( self.me.location) + (closest.location.flat_dist( self.friend_goal.location) / 400) for item in small_boosts: item_distance = item.location.flat_dist( self.me.location) + (item.location.flat_dist( self.friend_goal.location) / 400) if item_distance < closest_distance: item_loc = item.location.y * side(self.team) if (self.playstyle is self.playstyles.Offensive and item_loc < -2560 ) or ( self.playstyle is self.playstyles.Neutral and item_loc < -100) or ( self.playstyle is self.playstyles.Defensive and item_loc > 1280): closest = item closest_distance = item_distance if clear_on_valid: self.clear() self.push(goto_boost(closest)) return True return False
def goto_nearest_boost(self, only_small=False): if self.is_clear(): self.send_quick_chat(QuickChats.CHAT_TEAM_ONLY, QuickChats.Information_NeedBoost) if not only_small: large_boosts = ( boost for boost in self.boosts if boost.large and boost.active and ( (self.playstyle is self.playstyles.Offensive and boost.location.y * side(self.team) < -3000) or (self.playstyle is self.playstyles.Neutral and boost.location.y * side(self.team) > -100) or (self.playstyle is self.playstyles.Defensive and boost.location.y * side(self.team) > 3000))) closest = peek_generator(large_boosts) if closest is not None: closest_distance = closest.location.flat_dist( self.me.location) for item in large_boosts: item_distance = item.location.flat_dist( self.me.location) if item_distance is closest_distance: if item.location.flat_dist( self.me.location ) < closest.location.flat_dist(self.me.location): closest = item closest_distance = item_distance elif item_distance < closest_distance: closest = item closest_distance = item_distance self.push(goto_boost(closest)) return small_boosts = (boost for boost in self.boosts if not boost.large and boost.active) closest = peek_generator(small_boosts) if closest is not None: closest_distance = closest.location.flat_dist(self.me.location) for item in small_boosts: item_distance = item.location.flat_dist(self.me.location) if item_distance < closest_distance: item_loc = item.location.y * side(self.team) if (self.playstyle is self.playstyles.Offensive and item_loc < -2560 ) or ( self.playstyle is self.playstyles.Neutral and item_loc < -100) or ( self.playstyle is self.playstyles.Defensive and item_loc > 1280): closest = item closest_distance = item_distance self.push(goto_boost(closest))