示例#1
0
class Paul(BaseAgent):
    def initialize_agent(self):
        #self.gui = GUI() #Paul has a nice GUI that allows for drawing paths, creating and moving/editing events
        self.info = GameInfo(self.index, self.team)
        team = 0
        if self.team == 1:
            team = -1
        else:
            team = 1
        self.action_state = ''
        self.frames = 0
        self.yeet_start = time.time()
        self.yeet_kick_off = KickoffAgent('eat ass', self.info.team,
                                          self.info.index)
        self.last_frame = False
        self.flip_idx = 0
        self.lock = threading.Lock()
        self.fps = 60
        self.jump_frames = 0
        self.kick = True
        self.car_locations = [
            Queue(maxsize=4),
            Queue(maxsize=4),
            Queue(maxsize=4),
            Queue(maxsize=4),
            Queue(maxsize=4),
            Queue(maxsize=4)
        ]
        #self.orange_kickoff_hierarchy = [[2048, -2560, 0], [-2048, -2560, 0], [256, -3840, 0], [-256, -3840, 0]]
    def get_output(self, packet):
        self.info.read_packet(packet)
        game = self.convert_packet_to_v3(
            packet
        )  #Paul is a V3 Bot, a rework of preprocessing would be needed to re-optimize it
        self.frames = self.frames + 1
        self.renderer.begin_rendering()
        self.renderer.draw_string_2d(50, 50, 5, 5,
                                     str(time.time() - self.yeet_start),
                                     self.renderer.red())
        self.renderer.end_rendering()
        self.fps = self.frames / (time.time() - self.yeet_start)
        output = Bot.Process(self, game, packet, self.info, self.lock)
        controls = self.convert_output_to_v4(output)
        if (packet.game_info.is_kickoff_pause):
            controls = self.yeet_kick_off.get_output(
                packet, self.frames / (time.time() - self.yeet_start))
            self.last_frame = True

            return controls
        else:
            self.kick = True
            self.yeet_kick_off = KickoffAgent('eat ass', self.info.team,
                                              self.info.index)

        return controls

    def is_hot_reload_enabled(self):
        return False
示例#2
0
class Agent(BaseAgent):

    def __init__(self, name, team, index):
        self.info = GameInfo(index, team)
        self.controls = SimpleControllerState()
        self.action = None
        self.counter = 0

    def get_output(self, packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(packet)

        if self.action == None or self.action.finished or self.counter == 400:
            target_pos = vec3(
                random.uniform(-3000, 3000),
                random.uniform(-2000, 2000),
                25
            )

            target_speed = random.uniform(500, 2000)

            self.action = Drive(self.info.my_car, target_pos, target_speed)

            self.counter = 0

        r = 200
        self.renderer.begin_rendering()
        purple = self.renderer.create_color(255, 230, 30, 230)

        self.renderer.draw_line_3d(self.action.target_pos - r * vec3(1, 0, 0),
                                   self.action.target_pos + r * vec3(1, 0, 0),
                                   purple)

        self.renderer.draw_line_3d(self.action.target_pos - r * vec3(0, 1, 0),
                                   self.action.target_pos + r * vec3(0, 1, 0),
                                   purple)

        self.renderer.draw_line_3d(self.action.target_pos - r * vec3(0, 0, 1),
                                   self.action.target_pos + r * vec3(0, 0, 1),
                                   purple)
        self.renderer.end_rendering()



        if controller.L1:
            self.controls = controller.get_output()
        else:
            self.counter += 1
            if (self.counter % 10) == 0:
                print(f"current speed: {norm(self.info.my_car.vel):4.4f}, \
                        desired speed: {self.action.target_speed:4.4f}")

            self.action.step(0.01666)
            self.controls = self.action.controls



        return self.controls
示例#3
0
class ATBA(BaseAgent):
    def initialize_agent(self):
        self.info = GameInfo(self.index, self.team)

    def get_output(self, packet: GameTickPacket) -> SimpleControllerState:
        return SimpleControllerState()

    def atba_fast(self, packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(packet)
        return self.drive_controls(self.info.ball.pos, target_speed=Speed.fast)

    def atba_normal(self, packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(packet)
        return self.drive_controls(self.info.ball.pos, target_speed=Speed.normal)

    def atba_slow(self, packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(packet)
        return self.drive_controls(self.info.ball.pos, target_speed=Speed.slow)

    def atba_wait(self, packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(packet)
        return self.drive_controls(self.info.ball.pos, target_speed=Speed.stop)

    def drive_controls(self, target, target_speed):
        self.action = self.action = Drive(self.info.my_car, target_pos = target, target_speed=target_speed)
        self.action.step(1/60)
        return self.action.controls
示例#4
0
class KickoffAgent():
    def __init__(self, name, team, index):
        #This runs once before the bot starts up
        self.controller_state = SimpleControllerState()
        self.info = GameInfo(index, team)
        self.state = 'init'
        self.team = team

    def get_output(self, packet: GameTickPacket, fps) -> SimpleControllerState:

        self.info.read_packet(packet)
        if (self.state == 'init'):
            self.hit = Kickoff(info=self.info, fps=fps)
            self.state = 'run'
        #creating a basis for the field
        return self.hit.execute(self.info, fps).to_simple_controller_state()
示例#5
0
文件: snek.py 项目: robbai/RLBotPack
class Snek(BaseAgent):
    def __init__(self, name, team, index):
        super().__init__(name, team, index)
        self.info = GameInfo(index, team)
        self.last_turn = 0
        self.controls = SimpleControllerState()
        self.controls.throttle = 1
        self.controls.boost = 1

    def get_output(self, packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(packet)

        halfpi = math.pi / 2
        car = self.info.my_car
        ball = self.info.ball
        delta_local = dot(ball.pos - car.pos, car.theta)
        ang = math.atan2(delta_local[1], delta_local[0])

        car_state = CarState(boost_amount=100)

        if ang > math.pi / 2 and self.last_turn + TURN_COOLDOWN < time.time():
            self.last_turn = time.time()
            m = axis_rotation(vec3(0, 0, halfpi))
            nvel = dot(m, car.vel)
            nyaw = packet.game_cars[self.index].physics.rotation.yaw + halfpi
            car_state.physics = Physics(velocity=Vector3(
                nvel[0], nvel[1], nvel[2]),
                                        rotation=Rotator(pitch=0,
                                                         roll=0,
                                                         yaw=nyaw))

        if -ang > math.pi / 2 and self.last_turn + TURN_COOLDOWN < time.time():
            self.last_turn = time.time()
            m = axis_rotation(vec3(0, 0, -halfpi))
            nvel = dot(m, car.vel)
            nyaw = packet.game_cars[self.index].physics.rotation.yaw - halfpi
            car_state.physics = Physics(velocity=Vector3(
                nvel[0], nvel[1], nvel[2]),
                                        rotation=Rotator(pitch=0,
                                                         roll=0,
                                                         yaw=nyaw))

        game_state = GameState(cars={self.index: car_state})
        self.set_game_state(game_state)

        return self.controls
示例#6
0
class recover():
    def __init__(self,
                 master=None,
                 agent=None,
                 car=None,
                 target=None,
                 speed=None):
        self.name = 'RECOVER'
        self.master = master
        self.agent = agent
        self.car = car
        self.target = target
        self.speed = speed
        self.controls = SimpleControllerState()
        self.expired = False
        self.Ginfo = GameInfo(agent.index, agent.team)

    def update(self,
               master=None,
               agent=None,
               car=None,
               target=None,
               speed=None):
        self.master = master
        self.agent = agent
        self.car = car
        self.target = target
        self.speed = speed
        self.Ginfo = GameInfo(agent.index, agent.team)

    def available(self):
        return not self.car.has_wheel_contact

    def step(self, tick):
        self.Ginfo.read_packet(self.agent.packet)
        action = AerialTurn(self.Ginfo.my_car)
        action.step(tick)
        action.controls.throttle = 1

        self.expired = action.finished
        self.expired = self.car.has_wheel_contact

        return action.controls
示例#7
0
class BaseTestAgent(BaseAgent):
    def __init__(self, name, team, index):
        super(BaseTestAgent, self).__init__(name, team, index)
        self.action = self.create_action()
        self.info = GameInfo(index, team)

    def get_output(self,
                   game_tick_packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(game_tick_packet)
        self.test_process(game_tick_packet)
        return self.action.get_output(self.info)

    def create_action(self) -> BaseAction:
        raise NotImplementedError

    def test_process(self, game_tick_packet: GameTickPacket):
        raise NotImplementedError

    def initialize_agent(self):
        raise NotImplementedError
示例#8
0
class TorusChoreography(Choreography):
    def __init__(self, game_interface: GameInterface):
        super().__init__()
        self.game_interface = game_interface

        self.game_info = GameInfo(0, 0)
        self.renderer = self.game_interface.renderer
        self.drones_per_ring = 8

    def pre_step(self, packet: GameTickPacket, drones: List[Drone]):
        self.game_info.read_packet(packet)

    @staticmethod
    def get_num_bots():
        return 48

    def generate_sequence(self, drones):
        self.sequence.clear()

        if len(drones) == 0:
            return

        pause_time = 0.2

        self.sequence.append(HideBall())
        self.sequence.append(LetAllCarsSpawn(self.get_num_bots()))
        self.sequence.append(
            BlindBehaviorStep(SimpleControllerState(), pause_time))

        num_rings = len(drones) // self.drones_per_ring
        torus_period = 2 * math.pi / TORUS_RATE
        self.sequence.append(
            SubGroupOrchestrator(group_list=[
                TorusSubChoreography(
                    self.game_interface, self.game_info, -i * torus_period /
                    num_rings, drones[i * self.drones_per_ring:(i + 1) *
                                      self.drones_per_ring], 0)
                for i in range(0, num_rings)
            ]))
示例#9
0
class AerialStep(Step):
    """
    This uses the Aerial controller provided by RLUtilities. Thanks chip!
    It will take care of jumping off the ground and flying toward the target.
    This will only work properly if you call tick repeatedly on the same instance.
    """
    def __init__(self, target: Vec3, arrival_time: float, index: int):
        self.index = index
        self.aerial: Aerial = None
        self.game_info: GameInfo = None
        self.target = target
        self.arrival_time = arrival_time

    def tick(self, packet: GameTickPacket) -> StepResult:

        if self.game_info is None:
            self.game_info = GameInfo(self.index,
                                      packet.game_cars[self.index].team)
        self.game_info.read_packet(packet)

        if self.aerial is None:
            self.aerial = Aerial(
                self.game_info.my_car,
                vec3(self.target.x, self.target.y, self.target.z),
                self.arrival_time)

        self.aerial.step(SECONDS_PER_TICK)
        controls = SimpleControllerState()
        controls.boost = self.aerial.controls.boost
        controls.pitch = self.aerial.controls.pitch
        controls.yaw = self.aerial.controls.yaw
        controls.roll = self.aerial.controls.roll
        controls.jump = self.aerial.controls.jump

        return StepResult(controls,
                          packet.game_info.seconds_elapsed > self.arrival_time)
示例#10
0
class Agent(BaseAgent):

    def __init__(self, name, team, index):
        self.index = index
        self.info = GameInfo(index, team)
        self.controls = SimpleControllerState()

        self.skip = False
        self.timer = 0.0
        self.action = None
        self.car_predictions = []
        self.ball_predictions = []

        self.csign = 1;
        self.bsign = 1;

    def get_output(self, packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(packet)
        self.controls = SimpleControllerState()

        if self.timer == 0.0:

            self.csign = random.choice([-1, 1])

            # this just initializes the car and ball
            # to different starting points each time
            c_position = Vector3(random.uniform(-1000, 1000),
                                 random.uniform(-4500, -4000),
                                 25)

            car_state = CarState(physics=Physics(
                location=c_position,
                velocity=Vector3(0, 1000, 0),
                rotation=Rotator(0, 1.5 * self.csign, 0),
                angular_velocity=Vector3(0, 0, 0)
            ))

            self.bsign = random.choice([-1, 1])

            b_position = Vector3(random.uniform(-3500, -3000) * self.bsign,
                                 random.uniform(-1500,  1500),
                                 random.uniform(  150,   500))

            b_velocity = Vector3(random.uniform( 1000, 1500) * self.bsign,
                                 random.uniform(- 500,  500),
                                 random.uniform( 1000, 1500))

            ball_state = BallState(physics=Physics(
                location=b_position,
                velocity=b_velocity,
                rotation=Rotator(0, 0, 0),
                angular_velocity=Vector3(0, 0, 0)
            ))

            self.set_game_state(GameState(
                ball=ball_state,
                cars={self.index: car_state})
            )

            self.increment_timer = True

        if self.timer < 0.3:
            self.controls.throttle = 1 * self.csign
        else:
            if self.action == None:

                # set empty values for target and t_arrival initially
                self.action = Aerial(self.info.my_car, vec3(0,0,0), 0)

                # predict where the ball will be
                prediction = Ball(self.info.ball)
                self.ball_predictions = [vec3(prediction.pos)]

                for i in range(150):
                    prediction.step(0.016666)
                    prediction.step(0.016666)
                    self.ball_predictions.append(vec3(prediction.pos))

                    # if the ball is in the air
                    if prediction.pos[2] > 100:

                        self.action.target = prediction.pos
                        self.action.t_arrival = prediction.t

                        # check if we can reach it by an aerial
                        if self.action.is_viable():
                            break

            nsteps = 30
            delta_t = self.action.t_arrival - self.info.my_car.time
            prediction = Car(self.info.my_car)
            self.car_predictions = [vec3(prediction.pos)]
            for i in range(nsteps):
                prediction.step(Input(), delta_t / nsteps)
                self.car_predictions.append(vec3(prediction.pos))

            r = 200
            self.renderer.begin_rendering()
            purple = self.renderer.create_color(255, 230, 30, 230)
            white  = self.renderer.create_color(255, 230, 230, 230)

            x = vec3(r,0,0)
            y = vec3(0,r,0)
            z = vec3(0,0,r)
            target = self.action.target
            future = self.action.target - self.action.A

            self.renderer.draw_polyline_3d(self.ball_predictions, purple)
            self.renderer.draw_line_3d(target - x, target + x, purple)
            self.renderer.draw_line_3d(target - y, target + y, purple)
            self.renderer.draw_line_3d(target - z, target + z, purple)

            self.renderer.draw_polyline_3d(self.car_predictions, white)
            self.renderer.draw_line_3d(future - x, future + x, white)
            self.renderer.draw_line_3d(future - y, future + y, white)
            self.renderer.draw_line_3d(future - z, future + z, white)
            self.renderer.end_rendering()

            self.action.step(1.0 / 60.0)
            self.controls = self.action.controls

            if self.action.finished or self.timer > 10.0:
                self.timer = 0.0
                self.action = None
                self.increment_timer = False
                self.predictions = []

        if self.increment_timer:
            self.timer += 1.0 / 60.0

        self.info.my_car.last_input.roll  = self.controls.roll
        self.info.my_car.last_input.pitch = self.controls.pitch
        self.info.my_car.last_input.yaw   = self.controls.yaw
        self.info.my_car.last_input.boost = self.controls.boost

        return self.controls
示例#11
0
class BallPredictor:
    def __init__(self, index, team):
        self.index = index
        self.mass_car = 2.4
        self.mass_ball = 4.5
        self.car = CarModel(index)
        self.info = GameInfo(index, team)

    def update(packet):
        self.info.read_packet(packet)
        self.car.update(packet)

    def get_path( time, dt ):
        path = []
        t, path1, path2=self.will_hit( ball, self.car, time )
        newvel = self.predict_ball(ball, self.car)
        ball = Ball( self.info.ball )
        swapped = False
        for i in range(int(time/dt)):
            ball.step(dt)
            path.append(vec3(ball.pos))
            if i > t and not swapped:
                ball.vel = vec3(newvel[0].item(), newvel[1].item(), newvel[2].item())
                swapped = True
        return path

    def get_step( self, p1, p2 ):
        #Really bad Approximation
        distance = self.distance( p1, p2 )
        slopes = (p2 - p1)/distance
        return slopes

    def get_impact_point( self, loc ):
        step = self.get_step( self.car_pos, loc )
        current = self.car_pos
        while self.point_in_car( current ):
            current = current + step
        return current

    def point_in_car( self, point ):
        point = point - self.car_pos
        point = self.rotate_axis(point, -self.car_rot[0], 0)
        point = self.rotate_axis(point, -self.car_rot[1], 1)
        point = self.rotate_axis(point, -self.car_rot[2], 2)
        between = []
        for i in range(3):
            between.append( -self.car_dims[i].item()/2 < point[i].item() and point[i].item() < self.car_dims[i].item()/2 )
        return between[0] and between[1] and between[2]

    def rotate_axis( self, x, rotation, axis ):

        x = x.unsqueeze(0)
        if axis == 0:
            r_x = rotation
            R_x = np.array([[1, 0, 0],
                                [0, r_x.cos(), -1*r_x.sin()],
                                [0, r_x.sin(), r_x.cos()]])
            x = np.dot( x, R_x )

        if axis == 1:
            r_y = rotation
            R_y = np.array([[r_y.cos(), 0, r_y.sin()],
                                [0, 1, 0],
                                [-1*r_y.sin(), 0, r_y.cos()]])
            x = np.dot(x, R_y)

        if axis == 2:
            r_z = rotation
            R_z = np.array([[r_z.cos(), -1*r_z.sin(), 0],
                                [r_z.sin(), r_z.cos(), 0],
                                [0, 0, 1]])
            x = np.dot(x, R_z)
        return x[0]

    def distance( self, p1, p2 ):
        return np.sum( (p1 - p2)**2 )**0.5

    def predict_ball(self, ball_info, player_info):

        ball_pos, ball_vel, ball_avel = self.parse_ball_info( ball_info )
        self.car_pos, self.car_vel, self.car_rot, self.car_avel = player_info.pos, player_info.vel, player_info.rot, player_info.avel

        impact_pos = self.get_impact_point( ball_pos )

        impact_step_dir = self.get_step( impact_pos, ball_pos )

        # This will not be accurate at all!
        magnitude = self.distance(self.car_vel * self.mass_car, ball_vel * self.mass_ball)
        J = impact_step_dir * magnitude
        # This will be more accurate
        J_final = J #+ self.impulse_correction

        return ball_vel + J_final/self.mass_ball

    def parse_ball_info(self, ball):
        ball_pos = np.array([ball.pos[0],
                                 ball.pos[1],
                                 ball.pos[2]])
        ball_vel = np.array([ball.vel[0],
                                 ball.vel[1],
                                 ball.vel[2]])
        ball_avel = np.array([ball.omega[0],
                                  ball.omega[1],
                                  ball.omega[2]])
        return ball_pos, ball_vel, ball_avel
示例#12
0
class Agent(BaseAgent):
    def __init__(self, name, team, index):
        self.index = index
        self.info = GameInfo(index, team)
        self.controls = SimpleControllerState()

        self.timer = 0.0
        self.timeout = 3.0

        self.action = None
        self.state = State.RESET

    def get_output(self, packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(packet)
        self.controls = SimpleControllerState()

        next_state = self.state

        if self.state == State.RESET:

            self.timer = 0.0

            # put the car in the middle of the field
            car_state = CarState(
                physics=Physics(location=Vector3(0, 0, 20),
                                velocity=Vector3(1000, 0, 0),
                                rotation=Rotator(0, 0, 0),
                                angular_velocity=Vector3(0, 0, 0)))

            # put the ball somewhere out of the way
            ball_state = BallState(
                physics=Physics(location=Vector3(0, -3000, 100),
                                velocity=Vector3(0, 0, 0),
                                rotation=Rotator(0, 0, 0),
                                angular_velocity=Vector3(0, 0, 0)))

            self.set_game_state(
                GameState(ball=ball_state, cars={self.index: car_state}))

            next_state = State.WAIT

        if self.state == State.WAIT:

            if self.timer > 0.2:
                next_state = State.INITIALIZE

        if self.state == State.INITIALIZE:

            self.action = HalfFlip(self.info.my_car)

            next_state = State.RUNNING

        if self.state == State.RUNNING:

            self.action.step(0.01666)
            self.controls = self.action.controls

            if self.timer > self.timeout:
                next_state = State.RESET

        self.timer += 0.01666
        self.state = next_state

        return self.controls
示例#13
0
class AgentModule:
    def __init__(
        self,
        agent,
        bot_container,
        model1_path=None,
        model2_path=None,
        save_path=None,
        mode=0,
        render=False,
    ):
        """
        AgentModule.

        agent: The agent that this is running on
        model1_path: Path to load model to be trained from. Defaults to making a new one.
        model2_path: Path to load model to be learned from (Used for transfer learning only).
        save_path: Path to save the model being trained (Used only when mode is not 0). Defaults to not saving.
        mode: 0 - Just playing the game.
              1 - Real time learning from human teacher (Rendering should be enabled).
              2 - Transfer learning from model specified in model2.
        render: Boolean, forced rendering when mode = 1
        """

        self.training_history = [[], []]
        self.count = 1
        self.ticks_per_update = 60 * 60  #~60 seconds
        self.save_path = save_path

        model2_bot_num = 0

        self.flags = {
            "render": render or mode == 1,
            "train": mode == 1,
            "transfer": mode == 2
        }

        if self.flags["train"] and self.flags["transfer"]:
            raise Exception("Both train and transfer flags cannot be true.")

        self.info = GameInfo(agent.index, agent.team)
        self.bots = bot_container(agent)
        self.ui = TrainingUI(self.bots)
        self.model = ModelBox(self.bots.num_bots(), agent.index, agent.team)
        self.controls = SimpleControllerState()

        self.reader = None
        if self.flags["train"] or self.flags["transfer"]:
            from keyboard_interface import reader
            self.reader = reader
            self.reader.set_bot_num(self.bots.num_bots())

        if model1_path != None:
            self.model.load(model1_path)

        if self.flags["transfer"]:
            self.model2 = ModelBox(model2_bot_num, agent.index, agent.team)
            if model2_path != None:
                self.model2.load(model2_path)
        self.paused = True

    def get_output(self,
                   packet: GameTickPacket,
                   renderer=None) -> SimpleControllerState:
        self.info.read_packet(packet)
        bot_index = self.model.predict(packet=packet)

        if self.flags["train"] and not self.reader.training_paused:
            self.training_history[0].append(self.reader.intended_index)
            self.training_history[1].append(packet)
            if self.count % self.ticks_per_update == 0:
                self.model.fit(self.training_history[0],
                               packets=self.training_history[1])

        if not self.paused and self.reader.training_paused and self.save_path != None:
            self.model.save(self.save_path)

        if self.flags["transfer"]:
            self.training_history[0].append(self.reader.intended_index)
            self.training_history[1].append(packet)
            if self.count % self.ticks_per_update == 0:
                self.model2.fit(self.training_history[0],
                                packets=self.training_history[1])
            bot_index = self.model2.predict(packet=packet)

        self.count += 1

        if self.flags["render"]:
            if renderer == None:
                raise ValueError(
                    "Must specify renderer when rendering is used (mode is 1 or render is true)"
                )
            renderer.begin_rendering()
            if self.reader != None:
                self.ui.update_tick(bot_index, self.reader.intended_index)
                renderer.draw_string_2d(
                    220, 0, 2, 2,
                    "Paused: " + str(self.reader.training_paused),
                    renderer.white())
            else:
                self.ui.update_tick(bot_index, -1)
            self.ui.render(renderer)
            renderer.end_rendering()
        self.paused = self.reader.training_paused
        if self.paused:
            return self.bots.get_bot(index=self.reader.intended_index)(packet)
        return self.bots.get_bot(index=bot_index)(packet)
示例#14
0
class Agent(BaseAgent):
    def __init__(self, name, team, index):
        self.index = index
        self.info = GameInfo(index, team)
        self.controls = SimpleControllerState()

        self.timer = 0.0
        self.timeout = 2.0

        self.action = None
        self.state = State.RESET

    def get_output(self, packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(packet)
        self.controls = SimpleControllerState()

        next_state = self.state

        if self.state == State.RESET:

            self.timer = 0.0

            # put the car in the middle of the field
            car_state = CarState(
                physics=Physics(location=Vector3(0, 0, 20),
                                velocity=Vector3(0, 0, 0),
                                rotation=Rotator(0, 0, 0),
                                angular_velocity=Vector3(0, 0, 0)))

            theta = random.uniform(0, 6.28)
            pos = Vector3(sin(theta) * 1000.0, cos(theta) * 1000.0, 100.0)

            # put the ball somewhere out of the way
            ball_state = BallState(
                physics=Physics(location=pos,
                                velocity=Vector3(0, 0, 0),
                                rotation=Rotator(0, 0, 0),
                                angular_velocity=Vector3(0, 0, 0)))

            self.set_game_state(
                GameState(ball=ball_state, cars={self.index: car_state}))

            next_state = State.WAIT

        if self.state == State.WAIT:

            if self.timer > 0.2:
                next_state = State.INITIALIZE

        if self.state == State.INITIALIZE:

            # in this demonstration, we choose to dodge toward the ball
            c = self.info.my_car
            target = self.info.ball.pos
            self.action = AirDodge(c, 0.1, target)

            next_state = State.RUNNING

        if self.state == State.RUNNING:

            self.action.step(0.01666)
            self.controls = self.action.controls

            if self.timer > self.timeout:
                next_state = State.RESET

        self.timer += 0.01666
        self.state = next_state

        return self.controls
示例#15
0
class LeviAgent(BaseAgent):
    def __init__(self, name, team, index):
        super().__init__(name, team, index)
        sys.path.insert(0, path)  # this is for separate process imports
        import torch
        self.torch = torch
        self.empty_controller = SimpleControllerState()
        self.model_path = None
        self.model = None
        self.input_formatter = None
        self.output_formatter = None
        self.expected_time = None
        self.mood = 0.0

        # initialize kickoff
        self.info = None
        self.drive = None
        self.dodge = None
        self.controls = SimpleControllerState()
        self.kickoff = False
        self.kickoffStart = None
        self.time = 0
        self.FPS = 1 / 120
        self.kickoffTime = 0

    def load_config(self, config_object_header: ConfigHeader):
        self.model_path = config_object_header.get('model_path')

    def initialize_agent(self):
        self.model = self.get_model()
        self.input_formatter = self.create_input_formatter()
        self.output_formatter = self.create_output_formatter()
        self.model.load_state_dict(self.torch.load(self.get_file_path()))

        # initialize kickoff
        self.info = GameInfo(self.index, self.team, self.get_field_info())

    def get_file_path(self):
        return os.path.join(path, self.model_path)

    def get_output(self, packet):
        """
        Predicts an output given the input
        :param packet: The game_tick_packet
        :return:
        """
        if not packet.game_info.is_round_active:
            # self.time = None
            return self.empty_controller
        if packet.game_cars[self.index].is_demolished:
            return self.empty_controller
        if self.time >= packet.game_info.seconds_elapsed:
            return self.empty_controller

        # kickoffs
        self.FPS = packet.game_info.seconds_elapsed - self.time
        self.time = packet.game_info.seconds_elapsed
        self.info.read_packet(packet)
        self.set_mechanics()
        prev_kickoff = self.kickoff
        self.kickoff = packet.game_info.is_kickoff_pause
        if self.kickoff and not prev_kickoff:
            init_kick_off(self)
        if self.kickoff:
            kick_off(self)
            return self.controls

        # ML control
        arr = self.input_formatter.create_input_array([packet], batch_size=1)

        assert (arr[0].shape == (1, 3, 9))
        assert (arr[1].shape == (1, 5))

        output = self.advanced_step(arr)

        return self.output_formatter.format_model_output(output, [packet],
                                                         batch_size=1)[0]

    def set_mechanics(self):
        if self.drive is None:
            self.drive = Drive(self.info.my_car, self.info.ball.pos, 1399)
        if self.dodge is None:
            self.dodge = AirDodge(self.info.my_car, 0.25, self.info.ball.pos)

    def create_input_formatter(self):
        return LeviInputFormatter(self.team, self.index)

    def create_output_formatter(self):
        return LeviOutputFormatter(self.index)

    def get_model(self):
        from torch_model import SymmetricModel
        return SymmetricModel()

    def advanced_step(self, arr):
        arr = [self.torch.from_numpy(x).float() for x in arr]

        with self.torch.no_grad():
            output, t = self.model.forward(*arr)
        self.quick_chat(t)

        return output

    @staticmethod
    def create_agent_configurations(config: ConfigObject):
        super(LeviAgent, LeviAgent).create_agent_configurations(config)
        params = config.get_header(BOT_CONFIG_AGENT_HEADER)
        params.add_value('model_path',
                         str,
                         default=os.path.join('models', 'cool_atba.mdl'),
                         description='Path to the model file')

    def quick_chat(self, t):
        new_time = t.mean.item()

        if self.expected_time is None:
            self.expected_time = new_time
            return

        self.mood *= 0.995
        self.mood += (self.expected_time - new_time) * 0.005

        if self.mood > 0.075:
            self.send_quick_chat(False, random.choice(positive))
            self.mood = 0
        if self.mood < -0.075:
            self.send_quick_chat(False, random.choice(negative))
            self.mood = 0

        self.expected_time = new_time
示例#16
0
class Agent(BaseAgent):
    def __init__(self, name, team, index):
        self.info = GameInfo(index, team)
        self.controls = SimpleControllerState()

    def get_output(self, packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(packet)

        ball = self.info.ball
        car = self.info.my_car

        # the vector from the car to the ball in local coordinates:
        # delta_local[0]: how far in front of my car
        # delta_local[1]: how far to the left of my car
        # delta_local[2]: how far above my car
        delta_local = dot(ball.pos - car.pos, car.theta)

        # the angle between the direction the car is facing
        # and the in-plane local position of the ball
        phi = math.atan2(delta_local[1], delta_local[0])

        # a simple steering controller that is proportional to phi
        self.controls.steer = clip(2.5 * phi, -1.0, 1.0)

        # just set the throttle to 1 so the car is always moving forward
        self.controls.throttle = 1.0

        # draw some of the lines showing the angle phi (purple)
        # and the local coordinates:
        # delta_local[0]: red
        # delta_local[1]: green
        # delta_local[2]: blue
        self.renderer.begin_rendering()
        red = self.renderer.create_color(255, 255, 30, 30)
        green = self.renderer.create_color(255, 30, 255, 30)
        blue = self.renderer.create_color(255, 30, 30, 255)
        white = self.renderer.create_color(255, 230, 230, 230)
        gray = self.renderer.create_color(255, 130, 130, 130)
        purple = self.renderer.create_color(255, 230, 30, 230)

        f = car.forward()
        l = car.left()
        u = car.up()

        self.renderer.draw_line_3d(car.pos, car.pos + delta_local[0] * f, red)
        self.renderer.draw_line_3d(car.pos, car.pos + delta_local[1] * l,
                                   green)
        self.renderer.draw_line_3d(car.pos, car.pos + delta_local[2] * u, blue)
        self.renderer.draw_line_3d(car.pos, ball.pos, white)
        self.renderer.draw_line_3d(ball.pos, ball.pos - delta_local[2] * u,
                                   gray)
        self.renderer.draw_line_3d(car.pos, ball.pos - delta_local[2] * u,
                                   gray)

        radius = 200
        num_segments = 30
        angle = []
        for i in range(num_segments):
            c = math.cos(phi * float(i) / (num_segments - 1))
            s = math.sin(phi * float(i) / (num_segments - 1))
            angle.append(car.pos + radius * (c * f + s * l))

        self.renderer.draw_polyline_3d(angle, purple)
        self.renderer.end_rendering()

        if controller.L1:
            self.controls = controller.get_output()

        return self.controls
示例#17
0
class SniperBot(BaseAgent):
    AIMING = 0
    FLYING = 1
    KICKOFF = 2

    def __init__(self, name, team, index):
        super().__init__(name, team, index)
        self.controls = SimpleControllerState()
        self.info = GameInfo(self.index, self.team)
        self.t_index = 0
        self.standby_position = vec3(0, 0, 300)
        self.direction = vec3(0, 0, 1)
        self.state = self.KICKOFF
        self.shoot_time = 0
        self.last_pos = self.standby_position
        self.last_elapsed_seconds = 0
        self.kickoff_timer_edge = False
        self.ball_moved = False
        self.next_is_super = False
        self.doing_super = False
        self.hit_pos = vec3(0, 0, 0)
        self.standby_initiated = False

    def get_output(self, packet: GameTickPacket) -> SimpleControllerState:
        dt = packet.game_info.seconds_elapsed - self.last_elapsed_seconds
        self.last_elapsed_seconds = packet.game_info.seconds_elapsed
        self.info.read_packet(packet)

        ball_pos = self.info.ball.pos

        if not self.standby_initiated:
            self.initiate_standby(packet)

        if ball_pos[0] != 0 or ball_pos[1] != 0:
            self.ball_moved = True

        if ball_pos[0] == 0 and ball_pos[
                1] == 0 and self.info.my_car.boost == 34 and not self.state == self.KICKOFF and self.ball_moved:
            # Ball is placed at the center - assume kickoff
            self.state = self.KICKOFF
            self.ball_moved = False

        if self.state == self.KICKOFF:
            if packet.game_info.is_kickoff_pause:
                self.kickoff_timer_edge = True
            if ball_pos[0] != 0 or ball_pos[1] != 0 or (
                    self.kickoff_timer_edge
                    and not packet.game_info.is_kickoff_pause):
                self.shoot_time = self.info.time + AIM_DURATION_AFTER_KICKOFF + self.t_index
                self.controls.boost = False
                self.controls.roll = 0
                self.kickoff_timer_edge = False
                self.state = self.AIMING
                self.last_pos = self.standby_position

        elif self.state == self.AIMING:

            self.controls.boost = False
            self.controls.roll = 0
            self.hit_pos = self.predict_hit_pos()
            self.direction = d = normalize(self.hit_pos -
                                           self.standby_position)

            rotation = Rotator(math.asin(d[2]), math.atan2(d[1], d[0]), 0)
            car_state = CarState(
                Physics(location=to_fb(self.standby_position),
                        velocity=Vector3(0, 0, 0),
                        rotation=rotation,
                        angular_velocity=Vector3(0, 0, 0)))
            game_state = GameState(cars={self.index: car_state})
            self.set_game_state(game_state)

            self.render_aiming(self.hit_pos)

            if self.shoot_time < self.info.time:
                self.state = self.FLYING
                if self.next_is_super:
                    self.doing_super = True
                    self.next_is_super = False
                else:
                    self.doing_super = False

        elif self.state == self.FLYING:

            speed = SUPER_SPEED if self.doing_super else NORMAL_SPEED
            vel = self.direction * speed
            n_pos = self.last_pos + vel * dt

            car_state = CarState(
                Physics(location=to_fb(n_pos), velocity=to_fb(vel)))
            game_state = GameState(cars={self.index: car_state})
            self.set_game_state(game_state)

            self.last_pos = n_pos
            self.controls.boost = self.doing_super
            self.controls.roll = self.doing_super

            if abs(n_pos[0]) > 4080 or abs(
                    n_pos[1]) > 5080 or n_pos[2] < 0 or n_pos[2] > 2020:
                # Crash
                self.state = self.AIMING
                self.shoot_time = self.info.time + AIM_DURATION
                self.last_pos = self.standby_position
                self.next_is_super = self.info.my_car.boost >= 99

        self.render_aiming(self.hit_pos)

        return self.controls

    def predict_hit_pos(self):
        speed = SUPER_SPEED if self.next_is_super else NORMAL_SPEED
        ball_prediction = self.get_ball_prediction_struct()

        if ball_prediction is not None:
            TIME_PER_SLICES = 1 / 60.0
            SLICES = 360

            # Iterate to find the first location which can be hit
            for i in range(0, 360):
                time = i * TIME_PER_SLICES
                rlpos = ball_prediction.slices[i].physics.location
                pos = vec3(rlpos.x, rlpos.y, rlpos.z)
                dist = norm(self.standby_position - pos)
                travel_time = dist / speed
                if time + TIME_PER_SLICES > travel_time:
                    # Add small bias for aiming
                    tsign = -1 if self.team == 0 else 1
                    enemy_goal = vec3(0, tsign * -5030, 300)
                    bias_direction = normalize(pos - enemy_goal)
                    pos = pos + bias_direction * GOAL_AIM_BIAS_AMOUNT
                    return pos

            # Use last
            rlpos = ball_prediction.slices[SLICES - 1].physics.location
            return vec3(rlpos.x, rlpos.y, rlpos.z)

        return vec3(0, 0, 0)

    def render_aiming(self, pos):
        if self.state == self.AIMING or self.state == self.FLYING:
            self.renderer.begin_rendering()
            t = max(0, self.shoot_time - self.info.time)
            r = 50 + 400 * t
            self.draw_circle(pos, self.direction, r,
                             20 + int(r / (math.tau * 5)))
            if self.state != self.FLYING:
                l = self.direction * (70 + t * 100)
                self.renderer.draw_line_3d(pos - l, pos + l,
                                           self.renderer.team_color())
            else:
                s = 70
                x = vec3(s, 0, 0)
                y = vec3(0, s, 0)
                z = vec3(0, 0, s)
                self.renderer.draw_line_3d(pos - x, pos + x,
                                           self.renderer.team_color())
                self.renderer.draw_line_3d(pos - y, pos + y,
                                           self.renderer.team_color())
                self.renderer.draw_line_3d(pos - z, pos + z,
                                           self.renderer.team_color())
            self.renderer.end_rendering()

    def draw_circle(self, center: vec3, normal: vec3, radius: float,
                    pieces: int):
        # Construct the arm that will be rotated
        arm = normalize(cross(normal, center)) * radius
        angle = 2 * math.pi / pieces
        rotation_mat = axis_rotation(angle * normalize(normal))
        points = [center + arm]

        for i in range(pieces):
            arm = dot(rotation_mat, arm)
            points.append(center + arm)

        self.renderer.draw_polyline_3d(points, self.renderer.team_color())

    def initiate_standby(self, packet):
        self.standby_initiated = True
        snipers_on_team = 0
        for i in range(0, packet.num_cars):
            car = packet.game_cars[i]
            if car.team == self.team:
                if car.name == self.name:
                    self.t_index = snipers_on_team
                if car.name[:6] == "Sniper":
                    snipers_on_team += 1

        tsign = -1 if self.team == 0 else 1

        z = 300
        y = 5030
        spacing = 400

        if snipers_on_team == 1:
            self.standby_position = vec3(0, tsign * y, z)
        elif snipers_on_team == 2:
            self.standby_position = vec3(-400 + self.t_index * 800, tsign * y,
                                         z)
        else:
            # There are an even number of snipers on the team
            is_top_row = (self.t_index < snipers_on_team / 2)
            offset = spacing * (snipers_on_team - 2) / 4
            row_index = self.t_index if is_top_row else self.t_index - snipers_on_team / 2
            x = -offset + row_index * spacing
            self.standby_position = vec3(x, tsign * y, z + 150 * is_top_row)
示例#18
0
class Calculator(BaseAgent):
    def __init__(self, name, team, index):
        self.index          = index
        self.info           = GameInfo(index, team)
        self.team           = team
        self.controls       = SimpleControllerState()
        self.action         = None

        self.last_time      = 0.0
        self.dt             = 1.0 / 120.0

        self.goals          = 0

        self.timer          = 0.0
        self.kickoff_pos    = None
        self.state          = None
        self.target         = None
        self.target_speed   = 1800
        self.drift          = False

        #bot parameters
        self.target_range   = 200
        self.low_boost      = 25
        self.max_ball_dist  = 4000
        self.def_extra_dist = 800
        self.turn_c_quality = 20
        self.min_target_s   = 1000
        self.dodge_dist     = 400

        self.RLwindow = [0]*4


    def get_output(self, packet):
        self.info.read_packet(packet)

        #additional processing not done by RLU
        self.kickoff_pause  = packet.game_info.is_kickoff_pause
        self.round_active   = packet.game_info.is_round_active
        self.dt             = self.info.time - self.last_time
        self.last_time      = self.info.time
        self.last_touch     = packet.game_ball.latest_touch.player_name
        
        #trashtalk
        if packet.game_cars[self.index].score_info.goals == self.goals + 1:
            self.send_quick_chat(QuickChats.CHAT_EVERYONE, QuickChats.Reactions_Calculated)
            
        self.goals          = packet.game_cars[self.index].score_info.goals

        #resets controls each tick
        self.controls = SimpleControllerState()

        #choose state
        if not self.round_active:
            self.state = None
        elif not self.state == "kickoff":
            if self.kickoff_pause:
                self.kickoff_pos    = None
                self.action         = None
                self.timer          = 0.0
                self.state          = "kickoff"
        
            elif not self.info.my_car.on_ground and not isinstance(self.action, AirDodge):
                self.state          = "recovery"
                self.action         = self.action = AerialTurn(self.info.my_car)

            elif norm(self.info.my_goal.center - self.info.my_car.pos) > norm(self.info.my_goal.center - self.info.ball.pos) + self.def_extra_dist:
                self.action         = None
                self.target_speed   = 2300
                self.state          = "defence"
		
                if self.team == 0:
                    sign = -1
                else:
                    sign = 1
                
                #temporary 2v2 for Cow
                if len(self.info.teammates) > 0:
                    if self.info.ball.pos[1] > 0:
                        self.target = vec3(3000,sign*4000,0)
                    else:
                        self.target = vec3(-3000,sign*4000,0)
                else:
                    self.target = vec3(0,sign*4000,0)

            elif self.info.my_car.pos[1] > 5120 or self.info.my_car.pos[1] < -5120:
                self.target         = vec3(0,5000,0) if self.info.my_car.pos[1] > 5120 else vec3(0,-5000,0)
                self.action         = self.action = Drive(self.info.my_car,self.target,1000)
                self.state          = "goal escape"

            elif self.state == None:
                self.action         = None
                self.target         = None
                self.target_speed   = 2300
                self.state          = "offence"


        #kickoff state
        if self.state == "kickoff":
            Kickoff.kickoff(self)

            #exit kickoff state
            if self.timer >= 2.6 or self.last_touch != '':
                self.state  = None
                self.action = None

        #recovery state
        elif self.state == "recovery":
            self.action.step(self.dt)
            self.controls           = self.action.controls
            self.controls.throttle  = 1.0
            
            #exit recovery state
            if self.info.my_car.on_ground == True:
                self.state  = None
                self.action = None


        #defence state and offence state
        elif self.state == "defence" or self.state == "offence":  
            #select target
            if self.target == None:
                #large boost
                if self.info.my_car.boost <= self.low_boost and norm(self.info.my_car.pos - self.info.ball.pos) > self.max_ball_dist:
                    active_pads = []
                    for pad in self.info.boost_pads:
                        if pad.is_active:
                            active_pads.append(pad)

                    if len(active_pads) != 0:
                        closest_pad = active_pads[0]
                        for pad in active_pads:
                            if norm(pad.pos - self.info.ball.pos) < norm(closest_pad.pos - self.info.ball.pos):
                                closest_pad = pad
                        self.target = closest_pad.pos
                    else:
                        self.target = self.info.ball.pos

                #ball        
                else:
                    self.target = self.info.ball.pos

            forward_target  = dot(self.target - self.info.my_car.pos, self.info.my_car.theta)[0]
            right_target    = dot(self.target - self.info.my_car.pos, self.info.my_car.theta)[1]
            angle_to_target = math.atan2(right_target, forward_target)

            forward_goal    = dot(self.info.their_goal.center - self.info.my_car.pos, self.info.my_car.theta)[0]
            right_goal      = dot(self.info.their_goal.center - self.info.my_car.pos, self.info.my_car.theta)[1]
            angle_to_goal   = math.atan2(right_goal, forward_goal)

            #select maneuver
            if not isinstance(self.action, AirDodge):
                #shooting
                if norm(self.info.ball.pos - self.info.my_car.pos) < self.dodge_dist and (angle_to_target - (math.pi/10.0) <= angle_to_goal <= angle_to_target + (math.pi/10.0)): 
                    self.action = AirDodge(self.info.my_car,0.2,self.info.their_goal.center)
                    self.timer  = 0.0
                #dodging
                elif (-math.pi/24.0) <= angle_to_target <= (math.pi/24.0) and norm(self.info.my_car.vel) > 700 and norm(self.info.ball.pos - self.info.my_car.pos) > 1000 and not self.state == "defence":
                    self.action = AirDodge(self.info.my_car,0.2,self.target)
                    self.timer  = 0.0
                #Drive
                else:
                    self.action = Drive(self.info.my_car,self.target,self.target_speed)
                
            #exit AirDodge
            else:
                self.timer += self.dt
                if self.timer >= 0.5:
                    self.action = None
 
            #Drive
            if isinstance(self.action, Drive):
                speed = norm(self.info.my_car.vel)
                r = -6.901E-11 * speed**4 + 2.1815E-07 * speed**3 - 5.4437E-06 * speed**2 + 0.12496671 * speed + 157

                #handbrake
                self.drift = False
                if (math.pi/2.0) <= angle_to_target or angle_to_target <= (-math.pi/2.0):
                    self.drift = True

                #target speed 
                elif (norm(self.target - (self.info.my_car.pos + dot(self.info.my_car.theta,vec3(0,r,0)))) < r or norm(self.target - (self.info.my_car.pos + dot(self.info.my_car.theta,vec3(0,-r,0)))) < r) and not self.target_speed < self.min_target_s:
                    self.target_speed += -50
                    self.action = Drive(self.info.my_car,self.target,self.target_speed)
                elif self.target_speed < 1800:
                    self.target_speed += 50
                    self.action = Drive(self.info.my_car,self.target,self.target_speed)

            #maneuver tick
            if self.action != None:
                self.action.step(self.dt)
                self.controls   = self.action.controls
                self.controls.handbrake = self.drift

            #exit either state
            if (self.state == "defence" and norm(self.info.my_goal.center - self.info.my_car.pos) < norm(self.info.my_goal.center - self.info.ball.pos)) or (norm(self.target - self.info.my_car.pos) < self.target_range):
                self.state = None


        #goal escape state
        if self.state == "goal escape":
            self.action.step(self.dt)
            self.controls   = self.action.controls

            #exit goal escape state
            if not (self.info.my_car.pos[1] > 5120 or self.info.my_car.pos[1] < -5120):
                self.state  = None
                self.action = None

        if 'win32gui' in sys.modules:
            #finding the size of the Rocket League window
            def callback(hwnd, win_rect):
                if "Rocket League" in win32gui.GetWindowText(hwnd):
                    rect = win32gui.GetWindowRect(hwnd)
                    win_rect[0] = rect[0]
                    win_rect[1] = rect[1]
                    win_rect[2] = rect[2] - rect[0]
                    win_rect[3] = rect[3] - rect[1]

            self.RLwindow = [0] * 4
            win32gui.EnumWindows(callback, self.RLwindow)

        #Rendering
        Render.debug(self)
        Render.turn_circles(self)
        if not self.target == None:
            Render.target(self)
        

        return self.controls
示例#19
0
class Agent(BaseAgent):
    def __init__(self, name, team, index):
        self.index = index
        self.info = GameInfo(index, team)
        self.controls = SimpleControllerState()

        self.timer = 0.0
        self.action = None

    def get_output(self, packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(packet)
        self.controls = SimpleControllerState()

        if self.timer < 0.05:

            position = Vector3(random.uniform(-4000, 4000),
                               random.uniform(-3000, 3000),
                               random.uniform(500, 2000))

            velocity = Vector3(random.uniform(-1500, 1500),
                               random.uniform(-1500, 1500),
                               random.uniform(-1000, -500))

            rotation = Rotator(random.uniform(-1.5, 1.5),
                               random.uniform(-1.5, 1.5),
                               random.uniform(-1.5, 1.5))

            angular_velocity = Vector3(random.uniform(-3.0, 3.0),
                                       random.uniform(-3.0, 3.0),
                                       random.uniform(-3.0, 3.0))

            car_state = CarState(
                physics=Physics(location=position,
                                velocity=velocity,
                                rotation=rotation,
                                angular_velocity=angular_velocity))

            self.set_game_state(GameState(cars={self.index: car_state}))

        if self.timer > 0.10:

            if self.action == None:
                self.action = AerialTurn(self.info.my_car)

            self.renderer.begin_rendering()
            red = self.renderer.create_color(255, 255, 30, 30)
            self.renderer.draw_polyline_3d(self.action.trajectory, red)
            self.renderer.end_rendering()

            self.action.step(1.0 / 60.0)
            self.controls = self.action.controls

            self.timer += 1.0 / 60.0
            if self.action.finished or self.timer > 5.0:
                print("target:\n", self.action.target)
                print("theta:\n", self.action.car.theta)
                print()
                self.timer = 0.0
                self.action = None

        self.timer += 1.0 / 60.0
        return self.controls
示例#20
0
class hypebot(BaseAgent):
    def __init__(self, name, team, index):
        super().__init__(name, team, index)
        self.name = name
        self.team = team
        self.index = index
        self.defending = False
        self.info = None
        self.bounces = []
        self.drive = None
        self.catching = None
        self.dodge = None
        self.recovery = None
        self.dribble = None
        self.controls = SimpleControllerState()
        self.kickoff = False
        self.inFrontOfBall = False
        self.kickoffStart = None
        self.step = "Catching"
        self.time = 0
        self.FPS = 1 / 120
        self.p_s = 0.
        self.kickoffTime = 0

    def initialize_agent(self):
        self.info = GameInfo(self.index, self.team, self.get_field_info())

    def get_output(self, packet: GameTickPacket) -> SimpleControllerState:
        if packet.game_info.seconds_elapsed - self.time > 0:
            self.FPS = packet.game_info.seconds_elapsed - self.time
        self.time = packet.game_info.seconds_elapsed
        self.info.read_packet(packet)
        self.predict()
        self.set_mechanics()
        prev_kickoff = self.kickoff
        self.kickoff = packet.game_info.is_kickoff_pause
        self.defending = self.should_defending()
        if self.kickoff and not prev_kickoff:
            initKickOff(self)
        if self.kickoff or self.step == "Dodge2":
            kickOff(self)
        else:
            self.get_controls()
        self.render_string(str(self.step))
        if not packet.game_info.is_round_active:
            self.controls.steer = 0
        return self.controls

    def predict(self):
        self.bounces = []
        ball_prediction = self.get_ball_prediction_struct()
        for i in range(ball_prediction.num_slices):
            location = vec3(ball_prediction.slices[i].physics.location.x,
                            ball_prediction.slices[i].physics.location.y,
                            ball_prediction.slices[i].physics.location.z)
            prev_ang_vel = ball_prediction.slices[i -
                                                  1].physics.angular_velocity
            prev_normalized_ang_vel = normalize(
                vec3(prev_ang_vel.x, prev_ang_vel.y, prev_ang_vel.z))
            current_ang_vel = ball_prediction.slices[
                i].physics.angular_velocity
            current_normalized_ang_vel = normalize(
                vec3(current_ang_vel.x, current_ang_vel.y, current_ang_vel.z))
            if prev_normalized_ang_vel != current_normalized_ang_vel and location[
                    2] < 125:
                self.bounces.append((location, i * 1 / 60))

    def set_mechanics(self):
        if self.drive is None:
            self.drive = Drive(self.info.my_car, self.info.ball.pos, 1399)
        if self.catching is None:
            self.catching = Catching(self.info.my_car, self.info.ball.pos,
                                     1399)
        if self.recovery is None:
            self.recovery = AerialTurn(self.info.my_car)
        if self.dodge is None:
            self.dodge = AirDodge(self.info.my_car, 0.25, self.info.ball.pos)
        if self.dribble is None:
            self.dribble = Dribbling(self.info.my_car, self.info.ball,
                                     self.info.their_goal)

    def get_controls(self):
        if self.step == "Steer" or self.step == "Dodge2":
            self.step = "Catching"
        if self.step == "Catching":
            target = get_bounce(self)
            if target is None:
                self.step = "Defending"
            else:
                self.catching.target_pos = target[0]
                self.catching.target_speed = (distance_2d(
                    self.info.my_car.pos, target[0]) + 50) / target[1]
                self.catching.step(self.FPS)
                self.controls = self.catching.controls
                ball = self.info.ball
                car = self.info.my_car
                if distance_2d(ball.pos,
                               car.pos) < 150 and 65 < abs(ball.pos[2] -
                                                           car.pos[2]) < 127:
                    self.step = "Dribbling"
                    self.dribble = Dribbling(self.info.my_car, self.info.ball,
                                             self.info.their_goal)
                if self.defending:
                    self.step = "Defending"
                if not self.info.my_car.on_ground:
                    self.step = "Recovery"
                ball = self.info.ball
                if abs(ball.vel[2]) < 100 and sign(
                        self.team) * ball.vel[1] < 0 and sign(
                            self.team) * ball.pos[1] < 0:
                    self.step = "Shooting"
        elif self.step == "Dribbling":
            self.dribble.step(self.FPS)
            self.controls = self.dribble.controls
            ball = self.info.ball
            car = self.info.my_car
            bot_to_opponent = self.info.opponents[0].pos - self.info.my_car.pos
            local_bot_to_target = dot(bot_to_opponent, self.info.my_car.theta)
            angle_front_to_target = math.atan2(local_bot_to_target[1],
                                               local_bot_to_target[0])
            opponent_is_near = norm(vec2(bot_to_opponent)) < 2000
            opponent_is_in_the_way = math.radians(
                -10) < angle_front_to_target < math.radians(10)
            if not (distance_2d(ball.pos, car.pos) < 150
                    and 65 < abs(ball.pos[2] - car.pos[2]) < 127):
                self.step = "Catching"
            if self.defending:
                self.step = "Defending"
            if opponent_is_near and opponent_is_in_the_way:
                self.step = "Dodge"
                self.dodge = AirDodge(self.info.my_car, 0.25,
                                      self.info.their_goal.center)
            if not self.info.my_car.on_ground:
                self.step = "Recovery"
        elif self.step == "Defending":
            defending(self)
        elif self.step == "Dodge":
            self.dodge.step(self.FPS)
            self.controls = self.dodge.controls
            self.controls.boost = 0
            if self.dodge.finished and self.info.my_car.on_ground:
                self.step = "Catching"
        elif self.step == "Recovery":
            self.recovery.step(self.FPS)
            self.controls = self.recovery.controls
            if self.info.my_car.on_ground:
                self.step = "Catching"
        elif self.step == "Shooting":
            shooting(self)

    def render_string(self, string):
        self.renderer.begin_rendering('The State')
        if self.step == "Dodge1":
            self.renderer.draw_line_3d(self.info.my_car.pos, self.dodge.target,
                                       self.renderer.black())
        self.renderer.draw_line_3d(self.info.my_car.pos, self.bounces[0][0],
                                   self.renderer.blue())
        self.renderer.draw_string_2d(
            20, 20, 3, 3, string + " " + str(abs(self.info.ball.vel[2])) +
            " " + str(sign(self.team) * self.info.ball.vel[1]),
            self.renderer.red())
        self.renderer.end_rendering()

    def should_defending(self):
        ball = self.info.ball
        car = self.info.my_car
        our_goal = self.info.my_goal.center
        car_to_ball = ball.pos - car.pos
        in_front_of_ball = distance_2d(ball.pos, our_goal) < distance_2d(
            car.pos, our_goal)
        backline_intersect = line_backline_intersect(
            self.info.my_goal.center[1], vec2(car.pos), vec2(car_to_ball))
        return in_front_of_ball and abs(backline_intersect) < 2000
示例#21
0
class BoostHog(BaseAgent):
    def initialize_agent(self):
        self.info = GameInfo(self.index, self.team, self.get_field_info())
        self.controls = SimpleControllerState()
        self.phase = None
        self.targets = []
        self.guides = []
        self.active_pads = []
        self.plan_pads = []

    #plans a path using a bezier curve
    def pathplan(self):
        car = self.info.my_car
        k = 50  #number of guides on path
        p0_ = car.pos
        p1_ = car.pos + car.vel * 2  #compensation for velocity

        self.guides = []

        if len(self.targets) == 1:
            p2_ = self.targets[0]

            for i in range(k):
                self.guides.append(bezier(p0_, p1_, p2_, p2_, (i / k)))

        else:
            p2_ = self.targets[0] + normalize(
                self.targets[0] - self.targets[1]
            ) * 100  #number not final, adjusts curve so that car ends up facing next target
            p3_ = self.targets[0]
            for i in range(k):
                self.guides.append(bezier(p0_, p1_, p2_, p3_, (i / k)))

    #find any convenient boost along path and adds it as a target
    def convboost(self):
        for guide in self.guides:
            for pad in self.active_pads:
                if pad not in self.plan_pads and norm(
                        guide - pad.pos
                ) <= 300:  #number not final, distance from guide to potential convenient boost has to be less or equal to this number
                    self.plan_pads.append(pad)
                    self.targets.insert(0, pad.pos)
                    self.pathplan()
                    self.convboost()
                    break
            else:
                continue
            break

    def turn_radius(self):
        # https://docs.google.com/spreadsheets/d/1Hhg1TJqVUCcKIRmwvO2KHnRZG1z8K4Qn-UnAf5-Pt64/edit?usp=sharing
        car_speed = norm(self.info.my_car.vel)
        return (+156 + 0.1 * car_speed + 0.000069 * car_speed**2 +
                0.000000164 * car_speed**3 - 5.62 * 10**(-11) * car_speed**4)

    def get_output(self, packet: GameTickPacket) -> SimpleControllerState:
        self.info.read_packet(packet)

        if self.phase == None:
            self.phase = 1

        #phase 1: path-planning
        elif self.phase == 1:
            self.targets = [vec3(0, 0, 25)]  #TODO pick targets

            self.pathplan()

            #adds all active boost pads to this list, big boosts first
            self.active_pads = []
            for pad in self.info.boost_pads:
                if pad.is_active:
                    self.active_pads.append(pad)
            for pad in self.info.small_boost_pads:
                if pad.is_active:
                    self.active_pads.append(pad)

            self.plan_pads = []
            self.convboost()

        #elif self.phase == 2:
        #TODO follow path

        #debug prints
        if True:
            self.renderer.begin_rendering("debug")
            self.renderer.draw_string_2d(20, 20, 1, 1,
                                         "phase: " + str(self.phase),
                                         self.renderer.black())
            self.renderer.draw_string_2d(20, 40, 1, 1,
                                         "targets: " + str(len(self.targets)),
                                         self.renderer.black())
            self.renderer.draw_string_2d(20, 60, 1, 1,
                                         "guides: " + str(len(self.guides)),
                                         self.renderer.black())
            self.renderer.draw_string_2d(
                20, 80, 1, 1, "big pads: " + str(len(self.info.boost_pads)),
                self.renderer.black())
            self.renderer.draw_string_2d(
                20, 100, 1, 1,
                "small pads: " + str(len(self.info.small_boost_pads)),
                self.renderer.black())
            self.renderer.draw_string_2d(
                20, 120, 1, 1, "active pads: " + str(len(self.active_pads)),
                self.renderer.black())
            self.renderer.draw_string_2d(
                20, 140, 1, 1, "turn radius: " + str(self.turn_radius()),
                self.renderer.black())
            self.renderer.draw_string_2d(20, 160, 1, 1,
                                         "car direction: " + "test",
                                         self.renderer.black())
            self.renderer.end_rendering()

        #renders targets
        for i in range(len(self.targets)):
            self.renderer.begin_rendering("target" + str(i))
            render_target(self, self.targets[i])
            self.renderer.end_rendering()

        #renders path
        self.renderer.begin_rendering("path")
        self.renderer.draw_polyline_3d(self.guides, self.renderer.white())
        self.renderer.end_rendering()

        return self.controls