Пример #1
0
class Game(object):
    """
    The main game class that holds the gameloop.
    """
    def __init__(self, host, port, width, height):
        """
        Create a screen and define some game specific things.
        """
        self.host = host
        self.port = port
        self.width = width
        self.height = height

        self.players = {}

        pymlgame.init()
        self.screen = Screen(self.host, self.port, self.width, self.height)
        self.clock = Clock(5)
        self.running = True
        self.colors = [WHITE, BLUE, GREEN, CYAN, MAGENTA, YELLOW, RED]
        self.color_length = math.ceil(self.screen.height / len(self.colors))

        # surfaces
        self.game_board = None
        self.init_game_board()

        self.dots = Surface(self.screen.width, self.screen.height)

    def init_game_board(self):
        self.game_board = [
            0 for _ in range(self.screen.height * self.screen.width)
        ]
        indices = random.sample(
            range(self.screen.height * self.screen.width),
            random.randint(self.screen.width // 2,
                           (2 *
                            (self.screen.height * self.screen.width) // 3)))

        for index in indices:
            self.game_board[index] = 1

    def offset(self, width_idx, height_idx):
        return height_idx * self.screen.width + width_idx

    def board_value(self, width_idx, height_idx):
        if width_idx == -1 or height_idx == -1:
            return 0
        return self.game_board[self.offset(width_idx, height_idx)]

    def update(self):
        """
        Update the screens contents in every loop.
        """
        # this is not really neccesary because the surface is black after initializing
        self.dots.fill(BLACK)

        intermediate_buffer = self.game_board.copy()

        for h_index in range(self.screen.height):
            for w_index in range(self.screen.width):
                id_above = h_index - 1 if h_index - 1 >= 0 else -1
                id_left = w_index - 1 if w_index - 1 >= 0 else -1
                id_right = w_index + 1 if w_index + 1 < self.screen.width else -1
                id_bottom = h_index + 1 if h_index + 1 < self.screen.height else -1

                cell_offset = self.offset(w_index, h_index)

                alive_check = [
                    self.board_value(id_left, id_above),
                    self.board_value(w_index, id_above),
                    self.board_value(id_right, id_above),
                    self.board_value(id_left, h_index),
                    self.board_value(w_index, h_index),
                    self.board_value(id_right, h_index),
                    self.board_value(id_left, id_bottom),
                    self.board_value(w_index, id_bottom),
                    self.board_value(id_right, id_bottom),
                ]

                # count neighbours that are alive
                counter = Counter(alive_check)
                num_alive = counter[1]

                if self.game_board[cell_offset] == 0:
                    if num_alive == 3:
                        intermediate_buffer[cell_offset] = 1
                        self.dots.draw_dot(
                            (w_index, h_index),
                            self.colors[h_index // self.color_length])
                elif num_alive < 2:
                    intermediate_buffer[cell_offset] = 0
                elif 2 <= num_alive <= 3:
                    self.dots.draw_dot(
                        (w_index, h_index),
                        self.colors[h_index // self.color_length])
                else:
                    intermediate_buffer[cell_offset] = 0

        self.game_board = intermediate_buffer.copy()

    def render(self):
        """
        Send the current screen content to Mate Light.
        """
        self.screen.reset()
        self.screen.blit(self.dots)

        self.screen.update()
        self.clock.tick()

    def handle_events(self):
        """
        Loop through all events.
        """
        for event in pymlgame.get_events():
            if event.type == E_NEWCTLR:
                #print(datetime.now(), '### new player connected with uid', event.uid)
                self.players[event.uid] = {
                    'name': 'alien_{}'.format(event.uid),
                    'score': 0
                }
            elif event.type == E_DISCONNECT:
                #print(datetime.now(), '### player with uid {} disconnected'.format(event.uid))
                self.players.pop(event.uid)
            elif event.type == E_KEYDOWN:
                #print(datetime.now(), '###', self.players[event.uid]['name'], 'pressed', event.button)
                if event.button == 9:
                    self.init_game_board()
                else:
                    self.colors.append(self.colors.pop(0))
            elif event.type == E_PING:
                #print(datetime.now(), '### ping from', self.players[event.uid]['name'])
                pass

    def gameloop(self):
        """
        A game loop that circles through the methods.
        """
        try:
            while True:
                self.handle_events()
                self.update()
                self.render()
        except KeyboardInterrupt:
            pass
Пример #2
0
class Game(object):
    """
    The main game class that holds the gameloop.
    """
    def __init__(self, host, port, width, height):
        """
        Create a screen and define some game specific things.
        """
        self.host = host
        self.port = port
        self.width = width
        self.height = height

        self.players = {}

        pymlgame.init()
        self.screen = Screen(self.host, self.port,
                             self.width, self.height)
        self.clock = Clock(5)
        self.running = True
        self.colors = [WHITE, BLUE, GREEN, CYAN, MAGENTA, YELLOW, RED]
        self.color_length = math.ceil(self.screen.height / len(self.colors))

        # surfaces
        self.game_board = None
        self.init_game_board()

        self.dots = Surface(self.screen.width, self.screen.height)

    def init_game_board(self):
        self.game_board = [0 for _ in range(self.screen.height * self.screen.width)]
        indices = random.sample(
            range(self.screen.height * self.screen.width),
            random.randint(self.screen.width // 2, (2 * (self.screen.height * self.screen.width) // 3))
        )

        for index in indices:
            self.game_board[index] = 1

    def offset(self, width_idx, height_idx):
        return height_idx * self.screen.width + width_idx

    def board_value(self, width_idx, height_idx):
        if width_idx == -1 or height_idx == -1:
            return 0
        return self.game_board[self.offset(width_idx, height_idx)]

    def update(self):
        """
        Update the screens contents in every loop.
        """
        # this is not really neccesary because the surface is black after initializing
        self.dots.fill(BLACK)

        intermediate_buffer = self.game_board.copy()

        for h_index in range(self.screen.height):
            for w_index in range(self.screen.width):
                id_above = h_index - 1 if h_index - 1 >= 0 else -1
                id_left = w_index - 1 if w_index - 1 >= 0 else -1
                id_right = w_index + 1 if w_index + 1 < self.screen.width else -1
                id_bottom = h_index + 1 if h_index + 1 < self.screen.height else -1

                cell_offset = self.offset(w_index, h_index)

                alive_check = [
                    self.board_value(id_left, id_above),
                    self.board_value(w_index, id_above),
                    self.board_value(id_right, id_above),
                    self.board_value(id_left, h_index),
                    self.board_value(w_index, h_index),
                    self.board_value(id_right, h_index),
                    self.board_value(id_left, id_bottom),
                    self.board_value(w_index, id_bottom),
                    self.board_value(id_right, id_bottom),
                ]

                # count neighbours that are alive
                counter = Counter(alive_check)
                num_alive = counter[1]

                if self.game_board[cell_offset] == 0:
                    if num_alive == 3:
                        intermediate_buffer[cell_offset] = 1
                        self.dots.draw_dot((w_index, h_index), self.colors[h_index // self.color_length])
                elif num_alive < 2:
                    intermediate_buffer[cell_offset] = 0
                elif 2 <= num_alive <= 3:
                    self.dots.draw_dot((w_index, h_index), self.colors[h_index // self.color_length])
                else:
                    intermediate_buffer[cell_offset] = 0

        self.game_board = intermediate_buffer.copy()

    def render(self):
        """
        Send the current screen content to Mate Light.
        """
        self.screen.reset()
        self.screen.blit(self.dots)

        self.screen.update()
        self.clock.tick()

    def handle_events(self):
        """
        Loop through all events.
        """
        for event in pymlgame.get_events():
            if event.type == E_NEWCTLR:
                #print(datetime.now(), '### new player connected with uid', event.uid)
                self.players[event.uid] = {'name': 'alien_{}'.format(event.uid), 'score': 0}
            elif event.type == E_DISCONNECT:
                #print(datetime.now(), '### player with uid {} disconnected'.format(event.uid))
                self.players.pop(event.uid)
            elif event.type == E_KEYDOWN:
                #print(datetime.now(), '###', self.players[event.uid]['name'], 'pressed', event.button)
                if event.button == 9:
                    self.init_game_board()
                else:
                    self.colors.append(self.colors.pop(0))
            elif event.type == E_PING:
                #print(datetime.now(), '### ping from', self.players[event.uid]['name'])
                pass

    def gameloop(self):
        """
        A game loop that circles through the methods.
        """
        try:
            while True:
                self.handle_events()
                self.update()
                self.render()
        except KeyboardInterrupt:
            pass
Пример #3
0
class Game(object):
    """
    The main game class that holds the gameloop.
    """
    def __init__(self, host, port, width, height):
        """
        Create a screen and define some game specific things.
        """
        self.host = host
        self.port = port
        self.width = width
        self.height = height

        self.players = {}

        pymlgame.init()
        self.screen = Screen(self.host, self.port,
                             self.width, self.height)
        self.clock = Clock(15)
        self.running = True
        self.colors = [WHITE, BLUE, GREEN, CYAN, MAGENTA, YELLOW, RED]

        # surfaces
        self.corners = Surface(self.screen.width, self.screen.height)
        self.lines = Surface(int(self.screen.width / 2) - 2,
                             int(self.screen.height / 2) - 2)
        self.rects = Surface(int(self.screen.width / 2) - 2,
                             int(self.screen.height / 2) - 2)
        self.circle = Surface(int(self.screen.width / 2) - 2,
                              int(self.screen.height / 2) - 2)
        self.filled = Surface(int(self.screen.width / 2) - 2,
                              int(self.screen.height / 2) - 2)

    def update(self):
        """
        Update the screens contents in every loop.
        """
        # this is not really neccesary because the surface is black after initializing
        self.corners.fill(BLACK)
        self.corners.draw_dot((0, 0), self.colors[0])
        self.corners.draw_dot((self.screen.width - 1, 0), self.colors[0])
        self.corners.draw_dot((self.screen.width - 1, self.screen.height - 1),
                              self.colors[0])
        self.corners.draw_dot((0, self.screen.height - 1), self.colors[0])

        self.lines.fill(BLACK)
        self.lines.draw_line((1, 0), (self.lines.width - 1, 0), self.colors[1])
        self.lines.draw_line((0, 1), (0, self.lines.height - 1), self.colors[3])
        self.lines.draw_line((0, 0), (self.lines.width - 1,
                                      self.lines.height - 1), self.colors[2])

        self.rects.fill(BLACK)
        self.rects.draw_rect((0, 0), (int(self.rects.width / 2) - 1,
                                      self.rects.height),
                             self.colors[2], self.colors[3])
        self.rects.draw_rect((int(self.rects.width / 2) + 1, 0),
                             (int(self.rects.width / 2) - 1,
                              self.rects.height),
                             self.colors[3], self.colors[2])

        self.circle.fill(BLACK)
        radius = int(min(self.circle.width, self.circle.height) / 2) - 1
        self.circle.draw_circle((int(self.circle.width / 2) - 1,
                                 int(self.circle.height / 2) - 1), radius,
                                self.colors[4], self.colors[5])

        self.filled.fill(self.colors[6])

    def render(self):
        """
        Send the current screen content to Mate Light.
        """
        self.screen.reset()
        self.screen.blit(self.corners)
        self.screen.blit(self.lines, (1, 1))
        self.screen.blit(self.rects, (int(self.screen.width / 2) + 1, 1))
        self.screen.blit(self.circle, (0, int(self.screen.height / 2) + 1))
        self.screen.blit(self.filled, (int(self.screen.width / 2) + 1,
                                       int(self.screen.height / 2) + 1))

        self.screen.update()
        self.clock.tick()

    def handle_events(self):
        """
        Loop through all events.
        """
        for event in pymlgame.get_events():
            if event.type == E_NEWCTLR:
                #print(datetime.now(), '### new player connected with uid', event.uid)
                self.players[event.uid] = {'name': 'alien_{}'.format(event.uid), 'score': 0}
            elif event.type == E_DISCONNECT:
                #print(datetime.now(), '### player with uid {} disconnected'.format(event.uid))
                self.players.pop(event.uid)
            elif event.type == E_KEYDOWN:
                #print(datetime.now(), '###', self.players[event.uid]['name'], 'pressed', event.button)
                self.colors.append(self.colors.pop(0))
            elif event.type == E_KEYUP:
                #print(datetime.now(), '###', self.players[event.uid]['name'], 'released', event.button)
                self.colors.append(self.colors.pop(0))
            elif event.type == E_PING:
                #print(datetime.now(), '### ping from', self.players[event.uid]['name'])
                pass

    def gameloop(self):
        """
        A game loop that circles through the methods.
        """
        try:
            while True:
                self.handle_events()
                self.update()
                self.render()
        except KeyboardInterrupt:
            pass
Пример #4
0
class Game(object):
    """
    The main game class that holds the gameloop.
    """
    def __init__(self, host, port, width, height):
        """
        Create a screen and define some game specific things.
        """
        self.host = host
        self.port = port
        self.width = width
        self.height = height

        self.players = {}

        pymlgame.init()
        self.screen = Screen(self.host, self.port, self.width, self.height)
        self.clock = Clock(15)
        self.running = True
        self.colors = [WHITE, BLUE, GREEN, CYAN, MAGENTA, YELLOW, RED]

        # surfaces
        self.corners = Surface(self.screen.width, self.screen.height)
        self.lines = Surface(
            int(self.screen.width / 2) - 2,
            int(self.screen.height / 2) - 2)
        self.rects = Surface(
            int(self.screen.width / 2) - 2,
            int(self.screen.height / 2) - 2)
        self.circle = Surface(
            int(self.screen.width / 2) - 2,
            int(self.screen.height / 2) - 2)
        self.filled = Surface(
            int(self.screen.width / 2) - 2,
            int(self.screen.height / 2) - 2)

    def update(self):
        """
        Update the screens contents in every loop.
        """
        # this is not really neccesary because the surface is black after initializing
        self.corners.fill(BLACK)
        self.corners.draw_dot((0, 0), self.colors[0])
        self.corners.draw_dot((self.screen.width - 1, 0), self.colors[0])
        self.corners.draw_dot((self.screen.width - 1, self.screen.height - 1),
                              self.colors[0])
        self.corners.draw_dot((0, self.screen.height - 1), self.colors[0])

        self.lines.fill(BLACK)
        self.lines.draw_line((1, 0), (self.lines.width - 1, 0), self.colors[1])
        self.lines.draw_line((0, 1), (0, self.lines.height - 1),
                             self.colors[3])
        self.lines.draw_line((0, 0),
                             (self.lines.width - 1, self.lines.height - 1),
                             self.colors[2])

        self.rects.fill(BLACK)
        self.rects.draw_rect(
            (0, 0), (int(self.rects.width / 2) - 1, self.rects.height),
            self.colors[2], self.colors[3])
        self.rects.draw_rect(
            (int(self.rects.width / 2) + 1, 0),
            (int(self.rects.width / 2) - 1, self.rects.height), self.colors[3],
            self.colors[2])

        self.circle.fill(BLACK)
        radius = int(min(self.circle.width, self.circle.height) / 2) - 1
        self.circle.draw_circle(
            (int(self.circle.width / 2) - 1, int(self.circle.height / 2) - 1),
            radius, self.colors[4], self.colors[5])

        self.filled.fill(self.colors[6])

    def render(self):
        """
        Send the current screen content to Mate Light.
        """
        self.screen.reset()
        self.screen.blit(self.corners)
        self.screen.blit(self.lines, (1, 1))
        self.screen.blit(self.rects, (int(self.screen.width / 2) + 1, 1))
        self.screen.blit(self.circle, (0, int(self.screen.height / 2) + 1))
        self.screen.blit(
            self.filled,
            (int(self.screen.width / 2) + 1, int(self.screen.height / 2) + 1))

        self.screen.update()
        self.clock.tick()

    def handle_events(self):
        """
        Loop through all events.
        """
        for event in pymlgame.get_events():
            if event.type == E_NEWCTLR:
                #print(datetime.now(), '### new player connected with uid', event.uid)
                self.players[event.uid] = {
                    'name': 'alien_{}'.format(event.uid),
                    'score': 0
                }
            elif event.type == E_DISCONNECT:
                #print(datetime.now(), '### player with uid {} disconnected'.format(event.uid))
                self.players.pop(event.uid)
            elif event.type == E_KEYDOWN:
                #print(datetime.now(), '###', self.players[event.uid]['name'], 'pressed', event.button)
                self.colors.append(self.colors.pop(0))
            elif event.type == E_KEYUP:
                #print(datetime.now(), '###', self.players[event.uid]['name'], 'released', event.button)
                self.colors.append(self.colors.pop(0))
            elif event.type == E_PING:
                #print(datetime.now(), '### ping from', self.players[event.uid]['name'])
                pass

    def gameloop(self):
        """
        A game loop that circles through the methods.
        """
        try:
            while True:
                self.handle_events()
                self.update()
                self.render()
        except KeyboardInterrupt:
            pass
Пример #5
0
class Game:
    def __init__(self):
        pymlgame.init()

        self.screen = Screen()
        # self.screen = Screen(host='matelight')
        self.clock = Clock(5)

        self.map = Map('1-1')
        self.mario = Mario()

        self.world = self.map.render_pixmap()
        self.colmat = self.map.generate_collision_matrix()

        for y in range(self.map.height):
            print('%02d %02d ' % (y, self.convert_y(y)), end='')
            for x in range(self.map.width):
                print(self.colmat[x][y], end='')
            print()

        self.gameover = False

        self.camera = Camera(self.map.width, self.map.height)

    def collide(self, x, y):
        """
        Check for a collision on the given position.

        :param x: x coord to check for collision
        :type x: int
        :param y: y coord to check for collision
        :type y: int
        :returns: bool - Collision detected?
        """
        return self.colmat[int(x)][self.convert_y(int(y))]

    def convert_y(self, y):
        """
        Converts coords from bottom 0 to top 0 for drawing.

        :param y: y coord with 0 at the bottom
        :type y: int
        :returns: int - y coord with 0 at the top
        """
        return self.map.height - y - 1

    def update(self):
        vel_x = 0
        vel_y = 0
        # apply jump force
        vel_y + self.mario.jumping
        if self.mario.jumping == 2:
            self.mario.jumping = 1
        elif self.mario.jumping == 1:
            self.mario.jumping = 0
        # apply movement force
        vel_x + self.mario.moving
        # apply gravity/falling
        vel_y -= 1
        # Compute resulting velocity
        # Apply resulting velocity and update position
        new_x = self.mario.x + vel_x
        new_y = self.mario.y + vel_y
        print('X: %d -> %d' % (self.mario.x, new_x))
        print('Y: %d -> %d' % (self.mario.y, new_y))
        print('C: %d' % self.colmat[new_x][self.convert_y(new_y)])
        print('R: %d' % self.collide(new_x, self.convert_y(new_y)))
        # Check collisions between objects
        # If collision, resolve it by moving back
        old_y = self.mario.y
        if not self.collide(self.mario.x, new_y) > 0:
            self.mario.y = new_y
        if not self.collide(new_x, old_y) > 0:
            self.mario.x = new_x

        # out of map?
        if self.mario.y < 0 or self.mario.x + self.mario.width <= 0 or self.mario.x >= self.map.width:
            self.gameover = True

        # camera
        self.camera.update((self.mario.x, self.mario.y))

        # autowalk
        # self.mario.x += 1

    def render(self):
        self.screen.reset()

        self.screen.blit(self.world, (int(0 - self.camera.x),
                                      int(0 - (self.convert_y(self.camera.y) - self.camera.height))))
        self.screen.blit(self.mario.current, (int(self.mario.x - self.camera.x),
                                              int(self.convert_y(self.mario.y + self.mario.height) - (self.convert_y(self.camera.y) - self.camera.height))))

        self.screen.update()
        self.clock.tick()

    def handle_events(self):
        for event in pymlgame.get_events():
            if event.type == E_PING:
                print(datetime.now(), '# ping from', event.uid)
            else:
                print(datetime.now(), '# unknown event', event.uid, event.type)

    def start(self):
        try:
            while not self.gameover:
                self.handle_events()
                self.update()
                self.render()
                if self.gameover:
                    break
            print('game over!')
        except KeyboardInterrupt:
            pass