Exemplo n.º 1
0
    def lidar_west_pulse(self):
        """
        The lidar beam that travels west within the game.
        :return: a point of where the beam either hit a wall or a part of the environment.
        """
        pulse_x, pulse_y = self.snakeEnv.snake.head.pos()
        west_pulse = Point(pulse_x, pulse_y)
        west_wall = Point((-1) * (self.snakeEnv.screen_width / 2), pulse_y)

        hit_obstacle = False
        hit_apple = False

        while True:

            if west_pulse.x <= west_wall.x:
                hit_obstacle = True
                break

            if self.snakeEnv.snake.point_is_in_tail(west_pulse)[0]:
                hit_obstacle = True
                break

            if self.snakeEnv.current_food.point_is_in_food(west_pulse)[0]:
                hit_apple = True
                break

            west_pulse.offset(-1, 0)

        return (west_pulse, hit_obstacle, hit_apple)
        """
Exemplo n.º 2
0
    def lidar_north_west_pulse(self):
        """
        The lidar beam that travels north west within the game.
        :return: a point of where the beam either hit a wall or a part of the environment.
        """
        pulse_x, pulse_y = self.snakeEnv.snake.head.pos()
        north_west_pulse = Point(pulse_x, pulse_y)
        north_wall = Point(pulse_x, self.snakeEnv.screen_height / 2)
        west_wall = Point(((-1) * self.snakeEnv.screen_width) / 2, pulse_y)

        hit_obstacle = False
        hit_apple = False

        while True:

            if north_west_pulse.y >= north_wall.y or north_west_pulse.x <= west_wall.x:
                hit_obstacle = True
                break

            if self.snakeEnv.snake.point_is_in_tail(north_west_pulse)[0]:
                hit_obstacle = True
                break

            if self.snakeEnv.current_food.point_is_in_food(
                    north_west_pulse)[0]:
                hit_apple = True
                break

            north_west_pulse.offset(-1, 1)

        return (north_west_pulse, hit_obstacle, hit_apple)
        """
Exemplo n.º 3
0
    def __wall_distances(self, snake_head: Point,
                         direction: Direction) -> np.array:
        north_wall = Point(snake_head.x, 0)
        west_wall = Point(0, snake_head.y)
        south_wall = Point(snake_head.x, self.game.dimensions()[1])
        east_wall = Point(self.game.dimensions()[0], snake_head.y)

        snake_north_wall_dist = snake_head.distance(north_wall)
        snake_west_wall_dist = snake_head.distance(west_wall)
        snake_south_wall_dist = snake_head.distance(south_wall)
        snake_east_wall_dist = snake_head.distance(east_wall)

        if direction == Direction.UP:
            return np.array([
                snake_west_wall_dist, snake_north_wall_dist,
                snake_east_wall_dist
            ])

        if direction == Direction.RIGHT:
            return np.array([
                snake_north_wall_dist, snake_east_wall_dist,
                snake_south_wall_dist
            ])

        if direction == Direction.DOWN:
            return np.array([
                snake_east_wall_dist, snake_south_wall_dist,
                snake_west_wall_dist
            ])

        if direction == Direction.LEFT:
            return np.array([
                snake_south_wall_dist, snake_west_wall_dist,
                snake_north_wall_dist
            ])
Exemplo n.º 4
0
    def lidar_south_pulse(self):
        """
        The lidar beam that travels south within the game.
        :return: a point of where the beam either hit a wall or a part of the environment.
        """
        pulse_x, pulse_y = self.snakeEnv.snake.head.pos()
        south_pulse = Point(pulse_x, pulse_y)
        south_wall = Point(pulse_x, (-1) * (self.snakeEnv.screen_height / 2))

        hit_obstacle = False
        hit_apple = False

        while True:

            if south_pulse.y <= south_wall.y:
                hit_obstacle = True
                break

            if self.snakeEnv.snake.point_is_in_tail(south_pulse)[0]:
                hit_obstacle = True
                break

            if self.snakeEnv.current_food.point_is_in_food(south_pulse)[0]:
                hit_apple = True
                break

            south_pulse.offset(0, -1)

        return (south_pulse, hit_obstacle, hit_apple)
        """
Exemplo n.º 5
0
def distance_to_apple_percentage_tail_length_multiplier(env: SnakeEnv):
    def normalise(x):
        return 1 - (x / env.max_distance)

    food_x = env.current_food.head.xcor()
    food_y = env.current_food.head.ycor()
    food_point = Point(food_x, food_y)
    current_location = Point(env.snake.head.xcor(), env.snake.head.ycor())
    multiplier = len(env.snake.segments) if len(env.snake.segments) > 2 else 1
    return normalise(current_location.distance(food_point)) * multiplier
Exemplo n.º 6
0
    def __stop_lidar(self):
        """
        Gets the snakes 8 point lidar in it's starting position.
        :return:
        """
        lidar_pulses = [
            self.lidar_north_pulse(),
            self.lidar_north_east_pulse(),
            self.lidar_east_pulse(),
            self.lidar_south_east_pulse(),
            self.lidar_south_pulse(),
            self.lidar_south_west_pulse(),
            self.lidar_west_pulse(),
            self.lidar_north_west_pulse()
        ]
        lidar = np.zeros((len(lidar_pulses) * 3), dtype=np.float32)
        snake_x, snake_y = self.snakeEnv.snake.head.pos(
        )[0], self.snakeEnv.snake.head.pos()[1]
        snake_pos = Point(snake_x, snake_y)

        for i in range(len(lidar_pulses)):
            lidar_pulse = lidar_pulses[i]
            index = i * 3
            lidar[index] = snake_pos.distance(lidar_pulse[0])
            lidar[index + 1] = lidar_pulse[1]
            lidar[index + 2] = lidar_pulse[2]

        self.lidar_end_points = [
            lidar_pulse[0] for lidar_pulse in lidar_pulses
        ]

        return lidar
Exemplo n.º 7
0
    def __left_lidar(self):
        """
        Gets the Snake's 5 point lidar distances when it is facing left.

        Parameters:
            None

        Returns:
            lidar - A 1D numpy array with 5 entries, one for each lidar distance.
        """
        lidar_pulses = [
            self.lidar_south_pulse(),
            self.lidar_south_west_pulse(),
            self.lidar_west_pulse(),
            self.lidar_north_west_pulse(),
            self.lidar_north_pulse()
        ]
        lidar = np.zeros((len(lidar_pulses) * 3), dtype=np.float32)
        snake_x, snake_y = self.snakeEnv.snake.head.pos(
        )[0], self.snakeEnv.snake.head.pos()[1]
        snake_pos = Point(snake_x, snake_y)

        for i in range(len(lidar_pulses)):
            lidar_pulse = lidar_pulses[i]
            index = i * 3
            lidar[index] = snake_pos.distance(lidar_pulse[0])
            lidar[index + 1] = lidar_pulse[1]
            lidar[index + 2] = lidar_pulse[2]

        self.lidar_end_points = [
            lidar_pulses[0][0], lidar_pulses[1][0], lidar_pulses[2][0],
            lidar_pulses[3][0], lidar_pulses[4][0]
        ]

        return lidar
Exemplo n.º 8
0
    def __get_food_distance_reward(self, previous_location: Point,
                                   current_location: Point):
        """

        :param previous_location: A type point that specifies previous location of the environment
        :param current_location: A type point that specifies the current location of the environment
        :return: 1 if the environment moved towards the food, 0 if the environment moved away from the food
        """
        """
        food_x = self.current_food.head.xcor()
        food_y = self.current_food.head.ycor()
        food_point = Point(food_x, food_y)
        if (previous_location.distance(food_point) > current_location.distance(food_point)):
            return 1

        return 
        """
        def normalise(x):
            return 1 - (x / self.max_distance)

        food_x = self.current_food.head.xcor()
        food_y = self.current_food.head.ycor()
        food_point = Point(food_x, food_y)
        multiplier = len(
            self.snake.segments) if len(self.snake.segments) > 2 else 1
        return normalise(current_location.distance(food_point)) * multiplier
Exemplo n.º 9
0
    def __random_food(self) -> Point:
        available_slots = self.__available_food_positions()

        grid_slot = random.choice(tuple(available_slots))
        n_columns = self.screen_width / self.snake_size
        n_rows = self.screen_height / self.snake_size
        slot_x = grid_slot % n_columns
        slot_y = math.floor(grid_slot / n_rows)

        food_x = slot_x * self.snake_size
        food_y = slot_y * self.snake_size
        # self.food = pygame.Rect(food_x, food_y, self.snake_size, self.snake_size)
        return Point(food_x, food_y)
Exemplo n.º 10
0
 def start_position(self) -> Point:
     start_x = self.screen_width / 2
     start_y = self.screen_height / 2
     return Point(start_x, start_y)
Exemplo n.º 11
0
 def get_current_location(self):
     return Point(self.head.xcor(), self.head.ycor())