def main(): sm = SceneManager() sm.instantiate(sm) snd_mngr = SoundManager() snd_mngr.instantiate(snd_mngr) pl = Player('player.png', 400) pl.event.register_listener(snd_mngr.event_listener) pl.instantiate(pl, pygame.math.Vector2(0, 0), 0) item = Item() item.event.register_listener(pl.event_listener) item.instantiate(item) while (True): display.screen.fill((0, 50, 0)) gb.updateAll() event = pygame.event.poll() if event.type == pygame.QUIT: break #text = text_field.create_text("Hello, World", ["comicsansms"], 72, (0, 128, 0)) #display.screen.blit(text, #(320 - text.get_width() // 2, 240 - text.get_height() // 2)) pygame.display.flip() utils.clock.tick(60)
def __init__(self, resolution, level): super().__init__() self.sound = SoundManager() self.resolution = resolution self.state = res.STATE_RUNNING self.life = 3 self.level = level self.standard_shader = StandardShaderProgram() self.delta = 0.00001 self.light_setup = res.LightSetup( global_ambient=glm.vec3(0.3, 0.3, 0.3)) self.controls = res.GameControlState() self.model_registry = res.ModelRegistry() self.camera_id = 0 self.view_matrix = glm.mat4(1.0) self.maze_width = 30 self.maze_length = 30 self.maze = _setup_maze(self, self.maze_width, self.maze_length, depth=1.5) self._setup_systems() self._setup_entities() self._setup_level_objects() self.update_resolution(resolution)
def load(self): self.sprite_group = Group() self.label_font = self.res.font64 self.button_play = Button( self.res, ((WIDTH - self.res.image_button.get_width()) / 2, 240), 'Играть', self.sprite_group) self.button_drift = Button( self.res, ((WIDTH - self.res.image_button.get_width()) / 2, 300), 'Дрифт', self.sprite_group) self.button_shop = Button( self.res, ((WIDTH - self.res.image_button.get_width()) / 2, 360), 'Магазин', self.sprite_group) self.button_exit = Button( self.res, ((WIDTH - self.res.image_button.get_width()) / 2, 420), 'Выход', self.sprite_group) self.dollars = Dollars(self.res, self.sprite_group) self.sm = SoundManager(None, None) self.sm.set_background(self.res.music_bg_menu, 0.3) # Задний фон для меню self.world = b2World() self.world.gravity = 0, 0 self.contact_listener = ContactListener() self.world.contactListener = self.contact_listener self.obj_args = self.world, self.contact_listener, self.res self.animation_background = pygame.Surface((500, 300)).convert_alpha() self.animation_background.fill((0, 0, 0, 0)) self.background_group = Group() self.spawn_random_car() self.spawn_timer = 0 self.spawn_timeout = 1.5 self.spawn_counter = 0 self.background_camera = Camera(self.background_group)
def __init__(self): pg.init() pg.font.init() pg.display.set_caption("TETRIS") self.sound_manager = SoundManager() pg.mixer.music.load("Sounds/Music.mp3") pg.mixer.music.set_volume(0.3) pg.mixer.music.play(-1) self.main_surface = pg.display.set_mode((WINDOW_WIDTH, WINDOW_HEIGHT)) self.playground_surf = pg.Surface( (GRID_SIZE[0] * CELL_SIZE * UI_SCALE, GRID_SIZE[1] * CELL_SIZE * UI_SCALE)) self.next_surf = pg.Surface((220 * UI_SCALE, 220 * UI_SCALE)) self.font = pg.font.Font("Fonts/ARCADECLASSIC.TTF", int(FONT_SIZE * UI_SCALE)) if "top.scr" in os.listdir(): with open("top.scr") as file: self.top = int(file.read()) else: self.top = 0 self.score = 0 self.lines = 0 self.colors = np.zeros(GRID_SIZE, dtype=object) self.grid_colliders = np.zeros(GRID_SIZE) self.cur_shape = Shape(self, 5, -1) self.next_shape = Shape(self, 5, -1) self.game_over = False
class LevelState(GameState): def load(self): self.levels = Level.levels self.level = self.levels[self.asm.main.completed_levels] self.is_over = False self.saved = False self.over_timer = 0 self.over_timeout = 1 self.text = self.level[1] super().load() self.button = Button(self.res, (WIDTH - 120, HEIGHT - 70), 'Меню', self.sprite_group) self.minimap = Minimap(300, 240, self.sprite_group) self.conversation = Conversation(self.res, self.sprite_group) self.police_effect = PoliceEffect(self.sprite_group) self.energy_line = EnergyLine(self.res, self.sprite_group) self.dollars = Dollars(self.res, self.sprite_group, level=True) self.sm = SoundManager(self.conversation, self.car, self.sprite_group) self.load_map(self.level[0]) self.sm.player_car = self.car self.sm.set_background(self.res.music_bg_game, 0.1) def update(self, dt, events): self.dollars.value = self.car.dollars self.dollars.set_darkness_value(self.darkness.value) if self.is_over: self.over_timer += dt if self.over_timer >= self.over_timeout and not self.saved: self.saved = True if self.car.looted: self.asm.main.dollars += self.car.dollars self.asm.main.completed_levels = min( self.asm.main.completed_levels + 1, len(self.levels) - 1) self.asm.main.write_save() self.conversation.show( ['Esc - выход, Space - следующий уровень'], event_listener=self.end_event_listener) else: self.conversation.show(['Esc - выход, Space - начать заново'], event_listener=self.end_event_listener) if super().update(dt, events) is False: return self.energy_line.set_energy(self.car.energy) if not self.is_over and self.car.looted and not self.conversation.is_showing: self.conversation.show(['Вы победили'], lambda: self.__setattr__('is_over', True)) if not self.is_over and not self.car.energy and not self.conversation.is_showing: self.sm.set_background(self.res.sound_lose, 1) self.conversation.show(['Вы потеряли энергию, игра окончена'], lambda: self.__setattr__('is_over', True)) self.car.break_down()
def run_game(): # Initialize game, settings, and create a screen object. pygame.init() settings = Settings.getInstance() screen = pygame.display.set_mode( (settings.screen_width, settings.screen_height)) pygame.display.set_caption(settings.window_caption) # Make the Play button. play_button = Button(screen, "Play") # Make Groupmanager em = EntityManager.getInstance() # Make ship ship = Ship(screen) em.add_single("ship", ship) # Make a group to store bullets in. em.add_group("bullets") # Make a group to store aliens in em.add_group("aliens") # Create statistics and scoreboard stats = GameStats() sb = Scoreboard(settings, screen, stats) # Load background. bg = BackGround() # Create explosions group em.add_group("explosions") # Start background music SoundManager.getInstance().play_music() # Make power up group em.add_group("power_ups") # Start the main loop for the game. while True: # Watch for keyboard and mouse events. gf.check_events(screen, stats, sb, play_button) if stats.game_active: em.update_singles() gf.update_bullets(screen, stats, sb) gf.update_aliens(screen, stats, sb) gf.update_explosions() gf.update_power_ups() gf.update_screen(screen, bg, stats, sb, play_button)
def __init__(self, root): self.root = root self.canvas = Canvas(master=self.root.root, width=448, height=448) self.canvas.pack(side=TOP) self.canvas.bind('<Motion>', self.motion) #self.canvas.bind('<MouseWheel>', self.zoom) self.canvas.bind('<Button-1>', self.click) self.canvas.bind('<B1-Motion>', self.click) self.has_image = False self.zoom_level = 0 self.sound = SoundManager()
def create_explosion(screen, x, y): """ Creates an explosion """ # Generate indices in climbing order cols = settings.explosion_cols rows = settings.explosion_rows indices = [] for i in range(cols * rows): indices.append(i) # play explosion sound SoundManager.getInstance().explosion.play() # Return the explosion return Explosion(screen, x, y, (indices))
def check_keydown_events(event, screen): """Respond to keypresses.""" ship = ent_man.get_single("ship") if event.key == pygame.K_RIGHT: ship.moving_right = True elif event.key == pygame.K_LEFT: ship.moving_left = True elif event.key == pygame.K_SPACE: fire_bullet(screen) SoundManager.getInstance().laser.play() elif event.key == pygame.K_q: sys.exit(0)
class LevelTransition: """Displays a level transition""" TRANSITION_CHANNEL = 4 def __init__(self, screen, score_controller, transition_time=5000): self.screen = screen self.score_controller = score_controller self.sound = SoundManager(['GetLoud.wav'], keys=['transition'], channel=LevelTransition.TRANSITION_CHANNEL, volume=0.6) self.font = pygame.font.Font('fonts/LuckiestGuy-Regular.ttf', 32) self.ready_msg = self.font.render('Get Ready!', True, ScoreBoard.SCORE_WHITE) self.ready_msg_rect = self.ready_msg.get_rect() ready_pos = screen.get_width() // 2, int(screen.get_height() * 0.65) self.ready_msg_rect.centerx, self.ready_msg_rect.centery = ready_pos self.level_msg = None self.level_msg_rect = None self.transition_time = transition_time # total time to wait until the transition ends self.transition_begin = None self.transition_show = False def prep_level_msg(self): """Prepare a message for the current level number""" text = 'level ' + str(self.score_controller.level) self.level_msg = self.font.render(text, True, ScoreBoard.SCORE_WHITE) self.level_msg_rect = self.level_msg.get_rect() level_pos = self.screen.get_width() // 2, self.screen.get_height() // 2 self.level_msg_rect.centerx, self.level_msg_rect.centery = level_pos def set_show_transition(self): """Begin the sequence for displaying the transition""" self.prep_level_msg() self.transition_begin = pygame.time.get_ticks() self.transition_show = True self.sound.play('transition') def draw(self): """Display the level transition to the screen""" if abs(self.transition_begin - pygame.time.get_ticks()) > self.transition_time: self.transition_show = False else: self.screen.fill((0, 0, 0)) self.screen.blit(self.level_msg, self.level_msg_rect) if abs(self.transition_begin - pygame.time.get_ticks()) >= self.transition_time // 2: self.screen.blit(self.ready_msg, self.ready_msg_rect)
def __init__(self, screen, user, maze): self.screen = screen self.maze = maze self.user = user self.sound_manager = SoundManager( sound_files=['portal-open.wav', 'portal-travel.wav'], keys=['open', 'travel'], channel=PortalController.PORTAL_AUDIO_CHANNEL) self.blue_portal = pygame.sprite.GroupSingle( ) # portals as GroupSingle, which only allows one per group self.blue_projectile = None self.orange_portal = pygame.sprite.GroupSingle() self.orange_projectile = None # converter for projectile direction to portal direction self.portal_directions = {'l': 'r', 'r': 'l', 'u': 'd', 'd': 'u'}
def __create_game(self, gender, name, loadLast): self.started = True self.__clock = pygame.time.Clock() self.__sound_manager = SoundManager() app_loader = AppLoader(gender, name) bars_loader = app_loader.get_status_bars_loader() self.__game_man = app_loader.get_game_manager() if loadLast: self.load_game() # windows_controller asociado al screen self.windows_controller = SaludameWindowsController( self.__screen, self.__game_man) self.windows_controller.create_windows_and_activate_main( app_loader, self.__clock, bars_loader) #self.hotkeys_handler = HotKeyHandler() self.__game_man.start(self.windows_controller)
def __init__(self, screen, score_controller, transition_time=5000): self.screen = screen self.score_controller = score_controller self.sound = SoundManager(['pacman-beginning.wav'], keys=['transition'], channel=LevelTransition.TRANSITION_CHANNEL, volume=0.6) self.font = pygame.font.Font('fonts/LuckiestGuy-Regular.ttf', 32) self.ready_msg = self.font.render('Get Ready!', True, ScoreBoard.SCORE_WHITE) self.ready_msg_rect = self.ready_msg.get_rect() ready_pos = screen.get_width() // 2, int(screen.get_height() * 0.65) self.ready_msg_rect.centerx, self.ready_msg_rect.centery = ready_pos self.level_msg = None self.level_msg_rect = None self.transition_time = transition_time # total time to wait until the transition ends self.transition_begin = None self.transition_show = False
def load(self): super().load() self.button = Button(self.res, (WIDTH - 120, HEIGHT - 70), 'Меню', self.sprite_group) self.minimap = Minimap(300, 240, self.sprite_group) self.conversation = Conversation(self.res, self.sprite_group) self.police_effect = PoliceEffect(self.sprite_group) self.sm = SoundManager(self.conversation, self.car, self.sprite_group) self.load_map(self.res.drift_map_path) self.sm.player_car = self.car self.sm.set_background(self.res.music_bg_menu, 0.1) self.car.queue_lines.extend(['Свободный режим'])
def __init__(self): pygame.init() pygame.mixer.music.load('sounds/IDKMAN.wav') self.screen = pygame.display.set_mode( (800, 600) ) pygame.display.set_caption('PacMan Portal') self.clock = pygame.time.Clock() self.score_keeper = ScoreController(screen=self.screen, sb_pos=((self.screen.get_width() // 5), (self.screen.get_height() * 0.965)), items_image='cherry.png', itc_pos=(int(self.screen.get_width() * 0.6), self.screen.get_height() * 0.965)) self.maze = Maze(screen=self.screen, maze_map_file='maze_map.txt') self.life_counter = PacManCounter(screen=self.screen, ct_pos=((self.screen.get_width() // 3), (self.screen.get_height() * 0.965)), images_size=(self.maze.block_size, self.maze.block_size)) self.level_transition = LevelTransition(screen=self.screen, score_controller=self.score_keeper) self.game_over = True self.pause = False self.player = PacMan(screen=self.screen, maze=self.maze) self.ghosts = pygame.sprite.Group() self.ghost_sound_manager = SoundManager(sound_files=['RunForestRun.wav', 'Eaten3.wav', 'babySharkPacman.wav'], keys=['blue', 'eaten', 'std'], channel=Ghost.GHOST_AUDIO_CHANNEL) self.ghost_active_interval = 2500 self.ghosts_to_activate = None self.first_ghost = None self.other_ghosts = [] self.spawn_ghosts() self.actions = {PacManPortalGame.START_EVENT: self.init_ghosts, PacManPortalGame.REBUILD_EVENT: self.rebuild_maze, PacManPortalGame.LEVEL_TRANSITION_EVENT: self.next_level}
def __init__(self, screen, maze): super().__init__() self.screen = screen self.radius = maze.block_size // 5 self.maze = maze self.sound_manager = SoundManager(sound_files=['pacman-pellet-eat.wav', 'pacman-fruit-eat.wav', 'pacman-killed.wav', 'pacman-portal.wav'], keys=['eat', 'fruit', 'dead', 'portal'], channel=PacMan.PAC_AUDIO_CHANNEL) self.horizontal_images = ImageManager('pacman-horiz.png', sheet=True, pos_offsets=[(0, 0, 32, 32), (32, 0, 32, 32), (0, 32, 32, 32), (32, 32, 32, 32), (0, 64, 32, 32)], resize=(self.maze.block_size, self.maze.block_size), reversible=True) self.vertical_images = ImageManager('pacman-vert.png', sheet=True, pos_offsets=[(0, 0, 32, 32), (32, 0, 32, 32), (0, 32, 32, 32), (32, 32, 32, 32), (0, 64, 32, 32)], resize=(self.maze.block_size, self.maze.block_size), reversible=True) self.death_images = ImageManager('pacman-death.png', sheet=True, pos_offsets=[(0, 0, 32, 32), (32, 0, 32, 32), (0, 32, 32, 32), (32, 32, 32, 32), (0, 64, 32, 32), (32, 64, 32, 32)], resize=(self.maze.block_size, self.maze.block_size), animation_delay=150, repeat=False) self.flip_status = {'use_horiz': True, 'h_flip': False, 'v_flip': False} self.spawn_info = self.maze.player_spawn[1] self.tile = self.maze.player_spawn[0] self.direction = None self.moving = False self.speed = maze.block_size // 7 self.image, self.rect = self.horizontal_images.get_image() self.rect.centerx, self.rect.centery = self.spawn_info # screen coordinates for spawn self.dead = False self.portal_controller = PortalController(screen, self, maze) # controller object for portal # Keyboard related events/actions/releases self.event_map = {pygame.KEYDOWN: self.perform_action, pygame.KEYUP: self.reset_direction} self.action_map = {pygame.K_UP: self.set_move_up, pygame.K_LEFT: self.set_move_left, pygame.K_DOWN: self.set_move_down, pygame.K_RIGHT: self.set_move_right, pygame.K_q: self.blue_portal, pygame.K_w: self.orange_portal}
class LevelTransition: TRANSITION_CHANNEL = 4 def __init__(self, screen, score_controller, transition_time=5000): self.screen = screen self.score_controller = score_controller self.sound = SoundManager(['pacman-beginning.wav'], keys=['transition'], channel=LevelTransition.TRANSITION_CHANNEL, volume=0.6) self.font = pygame.font.Font('fonts/LuckiestGuy-Regular.ttf', 32) self.ready_msg = self.font.render('Get Ready!', True, ScoreBoard.WHITE) self.ready_msg_rect = self.ready_msg.get_rect() ready_pos = screen.get_width() // 2, int(screen.get_height() * 0.65) self.ready_msg_rect.centerx, self.ready_msg_rect.centery = ready_pos self.level_msg = None self.level_msg_rect = None self.transition_time = transition_time self.transition_begin = None self.transition_show = False def prep_level_msg(self): text = 'level ' + str(self.score_controller.level) self.level_msg = self.font.render(text, True, ScoreBoard.WHITE) self.level_msg_rect = self.level_msg.get_rect() level_pos = self.screen.get_width() // 2, self.screen.get_height() // 2 self.level_msg_rect.centerx, self.level_msg_rect.centery = level_pos def set_show_transition(self): self.prep_level_msg() self.transition_begin = pygame.time.get_ticks() self.transition_show = True self.sound.play('transition') def draw(self): if abs(self.transition_begin - pygame.time.get_ticks()) > self.transition_time: self.transition_show = False else: self.screen.fill((0, 0, 0)) self.screen.blit(self.level_msg, self.level_msg_rect) if abs(self.transition_begin - pygame.time.get_ticks()) >= self.transition_time // 2: self.screen.blit(self.ready_msg, self.ready_msg_rect)
def main(): GameData(SCREEN_TITLE) # SpriteCache() GameData.data['player_level'] = 1 GameData.data['player_xp'] = 0 window = arcade.Window(SCREEN_WIDTH, SCREEN_HEIGHT, SCREEN_TITLE) sound_manager = SoundManager(window) loading_view = menu_views.LoadingMenuView(window, sound_manager) window.show_view(loading_view) arcade.run()
def load(self): self.levels = Level.levels self.level = self.levels[self.asm.main.completed_levels] self.is_over = False self.saved = False self.over_timer = 0 self.over_timeout = 1 self.text = self.level[1] super().load() self.button = Button(self.res, (WIDTH - 120, HEIGHT - 70), 'Меню', self.sprite_group) self.minimap = Minimap(300, 240, self.sprite_group) self.conversation = Conversation(self.res, self.sprite_group) self.police_effect = PoliceEffect(self.sprite_group) self.energy_line = EnergyLine(self.res, self.sprite_group) self.dollars = Dollars(self.res, self.sprite_group, level=True) self.sm = SoundManager(self.conversation, self.car, self.sprite_group) self.load_map(self.level[0]) self.sm.player_car = self.car self.sm.set_background(self.res.music_bg_game, 0.1)
def __init__(self, config, level_name): self.config = config self.physics_manager = PhysicsManager() self.material_manager = MaterialManager(config["material_file"]) self.transmutation_manager = TransmutationManager(self.material_manager) self.transmutation_manager.blow_key = "stone" self.level = Level("{0}/{1}.lvl".format(config["levels_dir"], level_name), self.physics_manager, self.material_manager) self.main_char = Player.genMainCharacter() self.main_char.physical.position = [25, 10] self.level.actors.append(self.main_char) self.viewport = Viewport(config["width"], config["height"], self.main_char, self.level, 100) self.picking_handler = PickingHandler(self.viewport, self.transmutation_manager, self.physics_manager) self.ui_overlay = UIOverlay(config["font_file"]) self.ui_overlay.text_elements["score"] = TextElement((20, 20), 20, (0, 0, 0), "0 pts") self.physics_manager.add_actor(self.main_char) self._highlight_actors = False self.sound_manager = SoundManager() self.sound_manager.actors.append(self.main_char)
def start(self): #spawn initial GameObjects here like so: self._game.instantiate( Background(self._game, "Background", "background.png", 0, 0)) self._game.instantiate( SoundManager(self._game, "SoundManager", "unknown.png", -1, -1)) self._game.instantiate( UIManager(self._game, "UIManager", "unknown.png", -1, -1)) self.soundManager = self._game.getGameObjectByName("SoundManager") self.uiManager = self._game.getGameObjectByName("UIManager") #Music is here but I've disabled it for now #self.soundManager.play_music("background.wav") self._game.instantiate( Player(self._game, "Player", "player.png", 100, 500)) self.player = self._game.getGameObjectByName("Player") for i in range(0, 9): self._game.instantiate( Enemy(self._game, "Enemy", "enemy.png", 80 * i, 50)) self.scoreFont = pygame.font.Font('freesansbold.ttf', 16) self.gameOverFont = pygame.font.Font('freesansbold.ttf', 64)
class World(esper.World): def __init__(self, resolution, level): super().__init__() self.sound = SoundManager() self.resolution = resolution self.state = res.STATE_RUNNING self.life = 3 self.level = level self.standard_shader = StandardShaderProgram() self.delta = 0.00001 self.light_setup = res.LightSetup( global_ambient=glm.vec3(0.3, 0.3, 0.3)) self.controls = res.GameControlState() self.model_registry = res.ModelRegistry() self.camera_id = 0 self.view_matrix = glm.mat4(1.0) self.maze_width = 30 self.maze_length = 30 self.maze = _setup_maze(self, self.maze_width, self.maze_length, depth=1.5) self._setup_systems() self._setup_entities() self._setup_level_objects() self.update_resolution(resolution) def cleanup(self): """ cleanup... cleanup so what's the story behind this cleanup method why wouldn't I just use `__del__`? Well let me tell you the stupidest thing I've found in Python so far... Do you think that `del object` calls `object.__del__`? Well you would be kind of right because it does... but not right away. YES yes trust me. It queues the `__del__` call. This is usually fine but not here do you want to guess why? Well the `__del__` of the VBOs get called after the destruction of PyOpenGL. Now HOW, tell me HOW should I destruct a VBO if the OpenGL bindings are unavailable???? Now calm down and be happy that you've solved this bug after 4 total hours of debugging...... ~ xFrednet """ for _entity, vbo in self.get_component(StandardShaderVertexArray): vbo.cleanup() self.model_registry.cleanup() self.standard_shader.cleanup() print("World: Cleanup complete") def _setup_systems(self): # # Physics # consys.add_systems_1_to_world(self) psys.add_physics_systems_to_world(self) # # Rendering # # Prepare consys.add_systems_2_to_world(self) self.add_processor(rsys.PrepareFrameSystem()) rsys3d.add_systems_to_world(self) self.add_processor(rsys.FinishFrameSystem()) def _setup_entities(self): # Crappy mixed entity, OOP is a thing... well actually an object... # WTF. I'm always amazed by the comments I leave in my code. ~xFrednet 2020.09.23 position = glm.vec3(2.0, 2.0, 1.0) rotation = glm.vec3(0.0, 0.0, 0.0) self.player_object = self.create_entity( com.Model3D( self.model_registry.get_model_id(res.ModelRegistry.CUBE)), com.Transformation(position=position, rotation=rotation), com.TransformationMatrix(), com.ObjectMaterial(diffuse=glm.vec3(1.0, 0.3, 0.3)), com.Velocity(along_world_axis=False), com.Home(position, rotation), com.BoundingBox(com.Rectangle3D(1, 1, 1)), com.CollisionComponent(), com.PhysicsObject(), com.Light(attenuation=glm.vec3(0.1, 0.0, 1.0)), com.LightAnimation(base_color=glm.vec3(0.5, 0.2, 1.1), add_color=glm.vec3(0.1, 0.1, 0.1), delta_factor=0.5)) self.player_cam = self.create_entity( com.ThirdPersonCamera(self.player_object, distance=4.0, pitch=-0.5), com.CameraOrientation(), com.Transformation()) position = glm.vec3(-5.0, -5.0, 20.0) rotation = glm.vec3(0.9, -0.5, 0.0) self.free_cam = self.create_entity( com.Transformation(position=position, rotation=rotation), com.Velocity(along_world_axis=False, allow_paused=True), com.FreeCamera(), com.CameraOrientation(), com.Home(position, rotation)) self.camera_id = self.player_cam def _setup_level_objects(self): # Central light self.create_entity( com.Transformation(position=glm.vec3(self.maze.center.x, self.maze.center.y, 20.0)), com.Light(color=glm.vec3(0.5, 0.4, 0.4))) # ghost ghost_light_count = self.light_setup.MAX_LIGHT_COUNT - 2 - 1 min_val = min(self.maze_width, self.maze_length) ghosts = self.level * min_val * 0.2 # fallback if ghosts < 5: ghosts = 5 for i in range(int(ghosts)): coord = random.randint(0, len(self.maze.empty_areas_loc) - 1) r = random.random() g = random.random() b = random.random() x, y = self.maze.empty_areas_loc[coord] position = glm.vec3(x, y, 2.0) self.ghost = self.create_entity( com.Model3D( self.model_registry.get_model_id(res.ModelRegistry.GHOST)), com.Ghost(), com.Transformation(position=position, scale=glm.vec3(0.7, 0.7, 0.8)), com.TransformationMatrix(), com.ObjectMaterial(diffuse=glm.vec3(r, g, b)), com.Velocity(random.uniform(-1, 1), random.uniform(-1, 1), 0, along_world_axis=True), com.BoundingBox(com.Rectangle3D(1.4, 1.4, 3.0)), com.CollisionReport(), com.CollisionComponent(), com.PhysicsObject(), com.Home(position=position), com.Light(attenuation=glm.vec3(0.1, 0.0, 1.0), enabled=(i < ghost_light_count)), com.LightAnimation(base_color=glm.vec3(), add_color=glm.vec3(r, g, b), delta_factor=random.uniform(0.8, 1.4))) self.win_object = self.create_entity( com.Transformation(position=glm.vec3(self.maze.center.x, self.maze.center.y, 1.0)), com.Win(), com.Velocity(), com.BoundingBox(com.Rectangle3D(1.0, 1.0, 1.0)), com.CollisionReport(), com.Light(attenuation=glm.vec3(0.35, -0.36, 0.1)), com.LightAnimation(base_color=glm.vec3(1.0, 0.8, 0.0), add_color=glm.vec3(0.1, 0.1, 0.1))) def damage_player(self): self.sound.pause_music() self.sound.play_sound('damage') self.life -= 1 self.component_for_entity(self.player_object, com.ObjectMaterial).diffuse *= 0.7 self.sound.unpause_music() if self.life > 1: print(f'You have {self.life} lives left!') self.home_entities() elif self.life == 1: print(f'You have {self.life} life left!') self.home_entities() else: print('Game Over!') self.sound.stop_music() self.end_game() def won_game(self): self.sound.stop_music() self.sound.play_sound('win') print('You winted!') self.end_game(False) def end_game(self, lost=True): if lost: # to differentiate the sounds win/lost self.sound.play_sound('game_over') # Clear collisions for _id, collision in self.get_component(com.CollisionReport): collision.failed.clear() # Setup top-down camera transform = self.component_for_entity(self.free_cam, com.Transformation) transform.position.x = self.maze.center.x transform.position.y = self.maze.center.y transform.position.z = 50.0 transform.rotation = glm.vec3(0.0, -1.4, 0.0) self.controls.allow_camera_swap = False if self.controls.control_mode == res.GameControlState.PLAYER_MODE: self._swap_camera() # Animation self.component_for_entity(self.win_object, com.LightAnimation).enabled = False self.component_for_entity(self.win_object, com.Win).game_over = True def _swap_camera(self): controls: res.GameControlState = self.controls if controls.control_mode == res.GameControlState.PLAYER_MODE: self.camera_id = self.free_cam controls.control_mode = res.GameControlState.FREE_CAM_MODE self.state = res.STATE_PAUSED else: self.camera_id = self.player_cam controls.control_mode = res.GameControlState.PLAYER_MODE self.state = res.STATE_RUNNING def home_entities(self): for _id, (home, transformation, velocity) in self.get_components(com.Home, com.Transformation, com.Velocity): transformation.position = home.position transformation.rotation = home.rotation velocity.value = glm.vec3() def update_resolution(self, resolution): self.resolution = resolution self.standard_shader.update_projection_matrix(resolution)
class Main(GObject.Object): def __init__(self, target_size=(800, 600)): GObject.Object.__init__(self) self.__target_size = target_size self.gender = "boy" self.name = "" self.__screen = None self.__clock = None self.__game_over_callback = None self.__game_man = None self.__sound_manager = None self.__running = True self.started = False def set_game_over_callback(self, callback): self.__game_over_callback = callback def main(self, size, loadLast): if self.started: self.__game_man.reset_game(self.gender) else: self.__init(size) self.__create_game(self.gender, self.name, loadLast) self.__run() def __init(self, size): self.__target_size = size pygame.mixer.pre_init(22050, -16, 1, 512) pygame.mixer.init() pygame.mixer.music.set_endevent(pygame.USEREVENT) pygame.init() pygame.display.set_mode(self.__target_size, pygame.DOUBLEBUF, 0) self.__screen = pygame.display.get_surface() self.__screen.blit( pygame.image.load( os.path.join( BASEPATH, "assets/slides/screen_loading.jpg")).convert_alpha(), (0, 0)) pygame.display.flip() def __create_game(self, gender, name, loadLast): self.started = True self.__clock = pygame.time.Clock() self.__sound_manager = SoundManager() app_loader = AppLoader(gender, name) bars_loader = app_loader.get_status_bars_loader() self.__game_man = app_loader.get_game_manager() if loadLast: self.load_game() # windows_controller asociado al screen self.windows_controller = SaludameWindowsController( self.__screen, self.__game_man) self.windows_controller.create_windows_and_activate_main( app_loader, self.__clock, bars_loader) #self.hotkeys_handler = HotKeyHandler() self.__game_man.start(self.windows_controller) def __run(self): frames = 0 pygame.display.update() while self.__running: while Gtk.events_pending(): Gtk.main_iteration() self.__clock.tick( MAX_FPS) # waits if the game is running faster than MAX_FPS for event in pygame.event.get(): if event.type == pygame.KEYUP and event.key == pygame.K_ESCAPE: # Gdk.KEY_Escape print "FIXME:", pygame.KEYUP, pygame.K_ESCAPE self.__running = False self.save_game() elif event.type == pygame.MOUSEBUTTONDOWN: self.windows_controller.handle_mouse_down( pygame.mouse.get_pos()) elif event.type == pygame.MOUSEBUTTONUP: self.windows_controller.handle_mouse_up(event.pos) elif event.type == pygame.MOUSEMOTION: self.windows_controller.handle_mouse_motion(event.pos) elif event.type == pygame.VIDEOEXPOSE: self.windows_controller.reload_main = True elif event.type == pygame.USEREVENT and event.code == 0: # Music ended self.__sound_manager.start_playing() if self.__game_man.game_over: if self.__game_over_callback: self.__game_over_callback() else: self.__running = False else: self.windows_controller.update(frames) frames += 1 self.__game_man.signal() pygame.event.clear() pygame.display.update() print "FIXME: Se cuelga todo" pygame.quit() def save_game(self, path=INSTANCE_FILE_PATH): data = self.__game_man.serialize() try: f = open(path, 'w') f.write(data) finally: f.close() def load_game(self, path=INSTANCE_FILE_PATH): try: f = open(path) data = f.read() if self.__game_man: self.__game_man.parse_game(data) f.close() except: print "Error al cargar la partida" def volume_changed(self, range): value = range.get_value() if value >= 0 and value <= 10: value = float(value) / 10 self.__sound_manager.set_volume(value)
from constants import * from camera import Camera from player import Player from level import Level from lava import Lava from configuration import Configuration from sound_manager import SoundManager pygame.init() timer = pygame.time.Clock() surface = pygame.display.set_mode((WINDOW_WIDTH, WINDOW_HEIGHT)) pygame.display.set_icon(pygame.image.load('assets/gameicon.png')) pygame.display.set_caption('Speluncraft without craft') sound_manager = SoundManager() conf = Configuration() level = Level(CELL_SIZE, LEVEL_INITIAL_ROWS, LEVEL_INITIAL_COLS) player = Player(level, 0, PLAYER_SPAWN_POSITION_COL * CELL_SIZE, (SURFACE_LEVEL - 1 )* CELL_SIZE) lava = Lava() camera = Camera() font = pygame.font.SysFont("Verdana", 30) font_instructions = pygame.font.SysFont("Verdana", 16) mousex = 0 mousey = 0 player_score = 0
class GameInstance(object): def __init__(self, config, level_name): self.config = config self.physics_manager = PhysicsManager() self.material_manager = MaterialManager(config["material_file"]) self.transmutation_manager = TransmutationManager(self.material_manager) self.transmutation_manager.blow_key = "stone" self.level = Level("{0}/{1}.lvl".format(config["levels_dir"], level_name), self.physics_manager, self.material_manager) self.main_char = Player.genMainCharacter() self.main_char.physical.position = [25, 10] self.level.actors.append(self.main_char) self.viewport = Viewport(config["width"], config["height"], self.main_char, self.level, 100) self.picking_handler = PickingHandler(self.viewport, self.transmutation_manager, self.physics_manager) self.ui_overlay = UIOverlay(config["font_file"]) self.ui_overlay.text_elements["score"] = TextElement((20, 20), 20, (0, 0, 0), "0 pts") self.physics_manager.add_actor(self.main_char) self._highlight_actors = False self.sound_manager = SoundManager() self.sound_manager.actors.append(self.main_char) """ Internally sets and returns the tilesize required to display on the given screen """ def _recalc_tilesize(self, screen): self.tile_size = screen.get_width() / self.config["width_tiles"] return self.tile_size """ Clears the event queue and performs associated actions for the existing events """ def _handle_events(self, events): for event in events: event_name = event if isinstance(event, int) else event[0] if event_name == Actions.START_USER_LEFT: self.main_char.physical.velocity[0] -= self.config["user_motion_speed"] elif event_name == Actions.START_USER_RIGHT: self.main_char.physical.velocity[0] += self.config["user_motion_speed"] elif event_name == Actions.START_USER_UP: if self.main_char.physical.velocity[1] == 0: self.main_char.physical.velocity[1] -= self.config["user_jump_speed"] elif event_name == Actions.STOP_USER_LEFT: self.main_char.physical.velocity[0] += self.config["user_motion_speed"] elif event_name == Actions.STOP_USER_RIGHT: self.main_char.physical.velocity[0] -= self.config["user_motion_speed"] elif event_name == Actions.USER_SUCK: [self.transmutation_manager.suck(actor) for actor in self.level.actors if self.picking_handler.is_picked(actor, event[1])] elif event_name == Actions.USER_BLOW: (new_actor, tile_pos, weight) = self.transmutation_manager.blow(event[1], self.tile_size) new_actor.physical.position = tile_pos self.level.actors.append(new_actor) self.physics_manager.add_actor(new_actor) elif event_name == Actions.START_BLOW_SELECTION: self.picking_handler.start_user_selection(event[1], self.tile_size) elif event_name == Actions.STOP_BLOW_SELECTION: self.picking_handler.stop_user_selection() elif event_name == Actions.START_DISSOLVE_SELECTION: self._highlight_actors = True elif event_name == Actions.STOP_DISSOLVE_SELECTION: self._highlight_actors = False elif event_name == Actions.CHOOSE_MATERIAL: self.transmutation_manager.blow_key = event[1] elif event_name == Actions.MUTE: self.sound_manager.mute() elif event_name == Actions.UNMUTE: self.sound_manager.unmute() """ Updates all game objects and manager systems based on the frame time delta """ def _handle_updates(self, delta): self.sound_manager.update(delta) self.physics_manager.update(delta, self.tile_size) self.picking_handler.update(delta, self.tile_size) self.transmutation_manager.update(delta) self.ui_overlay.text_elements["score"].value = "{0} pts".format(self.transmutation_manager.current_points) self.ui_overlay.update(delta) self.level.update(delta, self.tile_size) self.viewport.update(delta) """ Renders all game objects to the screen """ def _render(self, screen): additional_drawables = [] mouse_position = pygame.mouse.get_pos() for actor in self.level.actors: if self._highlight_actors and self.picking_handler.is_picked(actor, mouse_position) and actor.dissolvable: picker = (pygame.Surface(actor.surface.get_size()), actor.position, True) picker[0].set_colorkey((0,0,0)) pygame.draw.rect(picker[0], tuple(self.config["picking_color"]), picker[0].get_rect(), 2) additional_drawables.append(picker) additional_drawables.append((self.picking_handler.surface, self.picking_handler.position, True)) additional_drawables += self.ui_overlay.get_drawables() screen.blit(self.viewport.render(additional_drawables), (0,0)) """ Handle events, update game state, and render to the given screen """ def doFrame(self, screen, delta, events): self._recalc_tilesize(screen) self._handle_events(events) self._handle_updates(delta) if self.level.is_player_at_goal(self.main_char): pygame.event.post(pygame.event.Event(CustomEvents.USERWINS)) self._render(screen)
def play_sound(self): """Play sound.""" SoundManager.play_audio(self.sound_path)
def __init__(self): self.twitter_feed = TwitterFeed() self.io = IOHandler() self.sound_manager = SoundManager()
class GameState: def __init__(self): self.twitter_feed = TwitterFeed() self.io = IOHandler() self.sound_manager = SoundManager() def update(self): if not self.io.active: self.io.was_active = False self.twitter_feed.reset() return if not self.io.was_active: self.io.was_active = True self.display_help() option = self.io.read() if option == '*': self.sound_manager.play('*') self.sound_manager.enqueue('load_more') self.twitter_feed.load_more() elif option == '#': self.display_help() return elif option != None: self.sound_manager.play(str(option)) self.sound_manager.enqueue('tweets/{0}'.format(self.twitter_feed.get_tweet(int(option)))) self.sound_manager.update() def display_help(self): self.sound_manager.play('intro')
class PortalController: """Manages portals and their related functionality within the game""" PORTAL_AUDIO_CHANNEL = 3 def __init__(self, screen, user, maze): self.screen = screen self.maze = maze self.user = user self.sound_manager = SoundManager( sound_files=['portal-open.wav', 'portal-travel.wav'], keys=['open', 'travel'], channel=PortalController.PORTAL_AUDIO_CHANNEL) self.blue_portal = pygame.sprite.GroupSingle( ) # portals as GroupSingle, which only allows one per group self.blue_projectile = None self.orange_portal = pygame.sprite.GroupSingle() self.orange_projectile = None # converter for projectile direction to portal direction self.portal_directions = {'l': 'r', 'r': 'l', 'u': 'd', 'd': 'u'} def clear_portals(self): """Remove all portals and projectiles""" self.blue_portal.empty() self.orange_portal.empty() self.blue_projectile = None self.orange_projectile = None def fire_b_portal_projectile(self): """Create a projectile for generating a blue portal""" if self.user.direction is not None: self.blue_projectile = PortalProjectile( screen=self.screen, source=self.user, direction=self.user.direction, p_type=Portal.P_TYPE_1) def fire_o_portal_projectile(self): """Create a projectile for generating an orange portal""" if self.user.direction is not None: self.orange_projectile = PortalProjectile( screen=self.screen, source=self.user, direction=self.user.direction, p_type=Portal.P_TYPE_2) def create_blue_portal(self, x, y, direction): """Create a blue portal, replacing the location it originally took up with a normal maze block""" if self.blue_portal: old_x, old_y = self.blue_portal.sprite.rect.x, self.blue_portal.sprite.rect.y self.maze.maze_blocks.add( Block(old_x, old_y, self.maze.block_size, self.maze.block_size, self.maze.block_image)) self.blue_portal.add( Portal(screen=self.screen, x=x, y=y, direction=direction, maze=self.maze, p_type=Portal.P_TYPE_1)) def create_orange_portal(self, x, y, direction): """Create a blue portal, replacing the location it originally took up with a normal maze block""" if self.orange_portal: old_x, old_y = self.orange_portal.sprite.rect.x, self.orange_portal.sprite.rect.y self.maze.maze_blocks.add( Block(old_x, old_y, self.maze.block_size, self.maze.block_size, self.maze.block_image)) self.orange_portal.add( Portal(screen=self.screen, x=x, y=y, direction=direction, maze=self.maze, p_type=Portal.P_TYPE_2)) def update(self): """Update the portal controller's display parts and tracking""" self.blue_portal.update() self.orange_portal.update() if self.blue_projectile: self.blue_projectile.update() # update projectile # erase projectile if it hits a portal if pygame.sprite.spritecollideany(self.blue_projectile, self.blue_portal) or \ pygame.sprite.spritecollideany(self.blue_projectile, self.orange_portal): self.blue_projectile = None return collision = pygame.sprite.spritecollideany(self.blue_projectile, self.maze.maze_blocks) if collision: # if projectile hits a block, replace it with a blue portal x, y = collision.rect.x, collision.rect.y collision.kill() # Replace the block with a portal direction = self.portal_directions[ self.blue_projectile.direction] self.blue_projectile = None # remove the projectile self.create_blue_portal(x, y, direction) self.sound_manager.play('open') # remove if projectile off screen elif self.blue_projectile.is_off_screen(): self.blue_projectile = None if self.orange_projectile: self.orange_projectile.update() # erase projectile if it hits a portal if pygame.sprite.spritecollideany(self.orange_projectile, self.blue_portal) or \ pygame.sprite.spritecollideany(self.orange_projectile, self.orange_portal): self.orange_projectile = None return collision = pygame.sprite.spritecollideany(self.orange_projectile, self.maze.maze_blocks) if collision: # if projectile hits a block, replace it with an orange portal x, y = collision.rect.x, collision.rect.y collision.kill() # Replace the block with a portal direction = self.portal_directions[ self.orange_projectile.direction] self.orange_projectile = None # remove the projectile self.create_orange_portal(x, y, direction) self.sound_manager.play('open') elif self.orange_projectile.is_off_screen(): self.orange_projectile = None def portables_usable(self): """Return True if the portables are usable (i.e. there are two of them)""" return self.blue_portal and self.orange_portal def collide_portals(self, other): """Return True if the sprite is colliding with any portal""" return pygame.sprite.spritecollideany(other, self.blue_portal) or \ pygame.sprite.spritecollideany(other, self.orange_portal) def check_portals(self, *args): """Check if other sprites have come into contact with the portals, and if so move them""" for arg in args: if pygame.sprite.spritecollideany( arg, self.blue_portal) and self.orange_portal: # get i, j as it relates to the maze map i, j = self.orange_portal.sprite.get_nearest_row( ), self.orange_portal.sprite.get_nearest_col() # move i or j based on portal direction if self.orange_portal.sprite.direction == 'l': j -= 1 elif self.orange_portal.sprite.direction == 'r': j += 1 elif self.orange_portal.sprite.direction == 'u': i -= 1 else: i += 1 # convert i, j to x, y coordinates using same formula as maze class x, y = ((self.screen.get_width()) // 5 + (j * self.maze.block_size)), \ ((self.screen.get_height()) // 12 + (i * self.maze.block_size)) arg.rect.x, arg.rect.y = x, y self.sound_manager.play('travel') elif pygame.sprite.spritecollideany( arg, self.orange_portal) and self.blue_portal: # get i, j as it relates to the maze map i, j = self.blue_portal.sprite.get_nearest_row( ), self.blue_portal.sprite.get_nearest_col() # move i or j based on portal direction if self.blue_portal.sprite.direction == 'l': j -= 1 elif self.blue_portal.sprite.direction == 'r': j += 1 elif self.blue_portal.sprite.direction == 'u': i -= 1 else: i += 1 # convert i, j to x, y coordinates using same formula as maze class x, y = ((self.screen.get_width() // 5) + (j * self.maze.block_size)), \ ((self.screen.get_height() // 12) + (i * self.maze.block_size)) arg.rect.x, arg.rect.y = x, y self.sound_manager.play('travel') def blit(self): """Blit the portal controller's display components to the screen""" if self.blue_projectile: self.blue_projectile.blit() if self.orange_projectile: self.orange_projectile.blit() if self.blue_portal: self.blue_portal.sprite.blit() if self.orange_portal: self.orange_portal.sprite.blit()
if closed_counter % fps == 0 and closed_counter > 0: if prev_closed_counter < closed_counter: sleep_frames = fps closed_counter = 0 open_counter = 0 closed_counter = max(closed_counter, 0) open_counter = max(open_counter, 0) # print('[open, closed, ratio] - [%s, %s, %s]' % (open_counter, closed_counter, ratio)) frame_with_msg = new_frame # add a sleeping warning to the frame if sleep_frames > 0: if sleep_frames == fps: SoundManager(sleep_detected=True) cv2.putText(new_frame, 'Sleeping', (80, 350), cv2.FONT_HERSHEY_SIMPLEX, 4, (0, 0, 255), 2, cv2.LINE_AA) sleep_frames -= 1 elif yawn_frames > 0: if yawn_frames == fps: SoundManager(sleep_detected=False) cv2.putText(new_frame, 'Drowsing', (80, 350), cv2.FONT_HERSHEY_SIMPLEX, 4, (0, 140, 255), 2, cv2.LINE_AA) yawn_frames -= 1 cv2.imshow('frame', new_frame) frames.append(new_frame)
MAIN_HERO = None NOW_LEVEL = None KOL_LEVELS = 8 # количество уровней # параметры героев (урон, скорость, здоровье) hero_parameters = namedtuple('hero_parameters', 'damage speed health') # name: (damage, speed, health) HEROES = { 'Ninja Frog': hero_parameters(15, 6, 100), 'Pink Man': hero_parameters(20, 5, 120), 'Virtual Guy': hero_parameters(15, 7, 95), 'Mask Dude': hero_parameters(15, 6, 100) } clock = pygame.time.Clock() # группы спрайтов all_sprites = pygame.sprite.Group() bullets_group = pygame.sprite.Group() checkpoints = pygame.sprite.Group() player_group = pygame.sprite.Group() fruits_group = pygame.sprite.Group() backpacks_group = pygame.sprite.Group() enemies_group = pygame.sprite.Group() potions_group = pygame.sprite.Group() chameleons = pygame.sprite.Group() spikes_group = pygame.sprite.Group() platforms = pygame.sprite.Group() sound_manager = SoundManager() # звуковой класс
class MainCanvas(): DEFAULT_SIZE = 448 INPUT_SIZE = 224 def __init__(self, root): self.root = root self.canvas = Canvas(master=self.root.root, width=448, height=448) self.canvas.pack(side=TOP) self.canvas.bind('<Motion>', self.motion) #self.canvas.bind('<MouseWheel>', self.zoom) self.canvas.bind('<Button-1>', self.click) self.canvas.bind('<B1-Motion>', self.click) self.has_image = False self.zoom_level = 0 self.sound = SoundManager() def new_image(self, img): self.current_image = img self.canvas.create_image(0, 0, image=img, anchor=NW) self.has_image = True def motion(self, event): ''' if self.has_image: self.canvas.delete("all") self.canvas.create_image(0,0,image=self.current_image,anchor=NW) size = MainCanvas.DEFAULT_SIZE * 2**self.zoom_level x = event.x - size y = event.y - size x = max(1, x) y = max(1, y) if x >= self.canvas.winfo_width() - size*2: x = self.canvas.winfo_width() - size*2 if y >= self.canvas.winfo_height() - size*2: y = self.canvas.winfo_height() - size*2 self.canvas.create_rectangle(x,y,x+size*2,y+size*2, width=3) self.current_pos = [x,y] ''' if self.has_image and self.zoom_level >= 0: self.canvas.delete("all") self.canvas.create_image(0, 0, image=self.current_image, anchor=NW) size = MainCanvas.DEFAULT_SIZE / MainCanvas.INPUT_SIZE * ( 2**self.zoom_level) x = event.x y = event.y x0 = round((event.x + 0.0) / size) * size y0 = round((event.y + 0.0) / size) * size self.canvas.create_rectangle(x0, y0, x0 + size, y0 + size) ''' def zoom(self, event): direction = -1 if event.delta > 1 else 1 self.zoom_level = direction + self.zoom_level if self.zoom_level < -3: self.zoom_level = -3 if self.zoom_level > 1: self.zoom_level = 1 self.motion(event) ''' def click(self, event): if self.has_image: if self.zoom_level == -1: self.root.keras_handler.whole_image() else: self.motion(event) x, y = self.change_coords(event.x, event.y) print(x, y, self.target[int(y)][int(x)]) if self.target[int(y)][int(x)] > 10: frequency = 400 + 14 * self.target[int(y)][int(x)] self.sound.sound_new(frequency=frequency, duration=0.05) def new_target_activation(self, activations): self.target = activations def change_coords(self, x, y): x = x / (MainCanvas.DEFAULT_SIZE / MainCanvas.INPUT_SIZE) y = y / (MainCanvas.DEFAULT_SIZE / MainCanvas.INPUT_SIZE) size = (2**self.zoom_level) x0 = round((x + 0.0) / size) * size y0 = round((y + 0.0) / size) * size return x0 / 2**self.zoom_level, y0 / 2**self.zoom_level
class PacMan(pygame.sprite.Sprite): """Represents the player character 'PacMan' and its related logic/control""" PAC_YELLOW = (255, 255, 0) PAC_AUDIO_CHANNEL = 0 def __init__(self, screen, maze): super().__init__() self.screen = screen self.radius = maze.block_size self.maze = maze self.sound_manager = SoundManager(sound_files=['pacman-pellet-eat.wav', 'Eaten1.wav', 'Eaten4.wav'], keys=['eat', 'fruit', 'dead'], channel=PacMan.PAC_AUDIO_CHANNEL) self.horizontal_images = ImageManager('pacman-horiz.png', sheet=True, pos_offsets=[(0, 0, 32, 32), (32, 0, 32, 32), (0, 32, 32, 32), (32, 32, 32, 32), (0, 64, 32, 32)], resize=(self.maze.block_size, self.maze.block_size), reversible=True) self.vertical_images = ImageManager('pacman-vert.png', sheet=True, pos_offsets=[(0, 0, 32, 32), (32, 0, 32, 32), (0, 32, 32, 32), (32, 32, 32, 32), (0, 64, 32, 32)], resize=(self.maze.block_size, self.maze.block_size), reversible=True) self.death_images = ImageManager('pacman-death.png', sheet=True, pos_offsets=[(0, 0, 32, 32), (32, 0, 32, 32), (0, 32, 32, 32), (32, 32, 32, 32), (0, 64, 32, 32), (32, 64, 32, 32)], resize=(self.maze.block_size, self.maze.block_size), animation_delay=150, repeat=False) self.flip_status = {'use_horiz': True, 'h_flip': False, 'v_flip': False} self.spawn_info = self.maze.player_spawn[1] self.tile = self.maze.player_spawn[0] self.direction = None self.moving = False self.speed = maze.block_size // 7 self.image, self.rect = self.horizontal_images.get_image() self.rect.centerx, self.rect.centery = self.spawn_info # screen coordinates for spawn self.dead = False # Keyboard related events/actions/releases self.event_map = {pygame.KEYDOWN: self.perform_action, pygame.KEYUP: self.reset_direction} self.action_map = {pygame.K_UP: self.set_move_up, pygame.K_LEFT: self.set_move_left, pygame.K_DOWN: self.set_move_down, pygame.K_RIGHT: self.set_move_right, } def set_death(self): """Set the death flag for PacMan and begin the death animation""" self.sound_manager.play('dead') self.dead = True self.image, _ = self.death_images.get_image() def revive(self): """Set dead to False and give PacMan a default image""" self.dead = False self.image, _ = self.horizontal_images.get_image() self.death_images.image_index = 0 def reset_position(self): """Reset position back to pre-define spawn location""" self.rect.centerx, self.rect.centery = self.spawn_info # screen coordinates for spawn def reset_direction(self, event): """Reset the movement direction if key-up on movement keys""" if event.key in (pygame.K_UP, pygame.K_DOWN, pygame.K_LEFT, pygame.K_RIGHT): self.moving = False def perform_action(self, event): """Change direction based on the event key""" if event.key in self.action_map: self.action_map[event.key]() def set_move_up(self): """Set move direction up""" if self.direction != 'u': self.direction = 'u' if self.flip_status['v_flip']: self.vertical_images.flip(False, True) self.flip_status['v_flip'] = False self.flip_status['use_horiz'] = False self.moving = True def set_move_left(self): """Set move direction left""" if self.direction != 'l': self.direction = 'l' if not self.flip_status['h_flip']: self.horizontal_images.flip() self.flip_status['h_flip'] = True self.flip_status['use_horiz'] = True self.moving = True def set_move_down(self): """Set move direction down""" if self.direction != 'd': self.direction = 'd' if not self.flip_status['v_flip']: self.vertical_images.flip(x_bool=False, y_bool=True) self.flip_status['v_flip'] = True self.flip_status['use_horiz'] = False self.moving = True def set_move_right(self): """Set move direction to right""" if self.direction != 'r': self.direction = 'r' if self.flip_status['h_flip']: self.horizontal_images.flip() self.flip_status['h_flip'] = False self.flip_status['use_horiz'] = True self.moving = True def get_nearest_col(self): """Get the current column location on the maze map""" return (self.rect.x - (self.screen.get_width() // 5)) // self.maze.block_size def get_nearest_row(self): """Get the current row location on the maze map""" return (self.rect.y - (self.screen.get_height() // 12)) // self.maze.block_size def is_blocked(self): """Check if PacMan is blocked by any maze barriers, return True if blocked, False if clear""" result = False if self.direction is not None and self.moving: original_pos = self.rect if self.direction == 'u': test = self.rect.move((0, -self.speed)) elif self.direction == 'l': test = self.rect.move((-self.speed, 0)) elif self.direction == 'd': test = self.rect.move((0, self.speed)) else: test = self.rect.move((self.speed, 0)) self.rect = test # temporarily move self # if any collision, result = True if pygame.sprite.spritecollideany(self, self.maze.maze_blocks): result = True elif pygame.sprite.spritecollideany(self, self.maze.shield_blocks): result = True self.rect = original_pos # reset position return result def update(self): """Update PacMan's position in the maze if moving, and if not blocked""" if not self.dead: if self.direction and self.moving: if self.flip_status['use_horiz']: self.image = self.horizontal_images.next_image() else: self.image = self.vertical_images.next_image() if not self.is_blocked(): if self.direction == 'u': self.rect.centery -= self.speed elif self.direction == 'l': self.rect.centerx -= self.speed elif self.direction == 'd': self.rect.centery += self.speed elif self.direction == 'r': self.rect.centerx += self.speed self.tile = (self.get_nearest_row(), self.get_nearest_col()) else: self.image = self.death_images.next_image() def blit(self): """Blit the PacMan sprite to the screen""" self.screen.blit(self.image, self.rect) def eat(self): """Eat pellets from the maze and return the score accumulated""" score = 0 fruit_count = 0 power = None collision = pygame.sprite.spritecollideany(self, self.maze.pellets) if collision: collision.kill() score += 10 self.sound_manager.play('eat') collision = pygame.sprite.spritecollideany(self, self.maze.fruits) if collision: collision.kill() score += 20 fruit_count += 1 self.sound_manager.play('fruit') collision = pygame.sprite.spritecollideany(self, self.maze.power_pellets) if collision: collision.kill() score += 20 power = True self.sound_manager.play('eat') return score, fruit_count, power
class TetrisGame: def __init__(self): pg.init() pg.font.init() pg.display.set_caption("TETRIS") self.sound_manager = SoundManager() pg.mixer.music.load("Sounds/Music.mp3") pg.mixer.music.set_volume(0.3) pg.mixer.music.play(-1) self.main_surface = pg.display.set_mode((WINDOW_WIDTH, WINDOW_HEIGHT)) self.playground_surf = pg.Surface( (GRID_SIZE[0] * CELL_SIZE * UI_SCALE, GRID_SIZE[1] * CELL_SIZE * UI_SCALE)) self.next_surf = pg.Surface((220 * UI_SCALE, 220 * UI_SCALE)) self.font = pg.font.Font("Fonts/ARCADECLASSIC.TTF", int(FONT_SIZE * UI_SCALE)) if "top.scr" in os.listdir(): with open("top.scr") as file: self.top = int(file.read()) else: self.top = 0 self.score = 0 self.lines = 0 self.colors = np.zeros(GRID_SIZE, dtype=object) self.grid_colliders = np.zeros(GRID_SIZE) self.cur_shape = Shape(self, 5, -1) self.next_shape = Shape(self, 5, -1) self.game_over = False def __del__(self): with open("top.scr", "w") as file: file.write(str(self.top)) def check_events(self): for event in pg.event.get(): if event.type == pg.QUIT: exit() if event.type == pg.KEYDOWN: if event.key == pg.K_SPACE: self.cur_shape.rotate() if event.key == pg.K_d: self.cur_shape.move(1) if event.key == pg.K_a: self.cur_shape.move(-1) def draw_surfaces(self): # Playground playground_pos = ((PLAYGROUND_POS[0] + UI_HORIZONTAL_OFFSET) * UI_SCALE, (PLAYGROUND_POS[1] + UI_VERTICAL_OFFSET) * UI_SCALE) self.main_surface.blit(self.playground_surf, playground_pos) # Next next_surf_pos = ((PLAYGROUND_POS[0] + GRID_SIZE[0] * CELL_SIZE + UI_HORIZONTAL_OFFSET + INFO_OFFSET) * UI_SCALE, (PLAYGROUND_POS[1] + GRID_SIZE[1] * CELL_SIZE - 220 + UI_VERTICAL_OFFSET) * UI_SCALE) self.main_surface.blit(self.next_surf, next_surf_pos) self.playground_surf.fill(BG_COLOR) self.next_surf.fill(BG_COLOR) def draw_ui(self): # Playground play_rect = ((PLAYGROUND_POS[0] + UI_HORIZONTAL_OFFSET) * UI_SCALE, (PLAYGROUND_POS[1] + UI_VERTICAL_OFFSET) * UI_SCALE, GRID_SIZE[0] * CELL_SIZE * UI_SCALE, GRID_SIZE[1] * CELL_SIZE * UI_SCALE) pg.draw.rect(self.main_surface, LINE_COLOR, play_rect, 3) # Top top_headline = self.font.render("TOP", False, TEXT_COLOR) top_headline_pos = ((PLAYGROUND_POS[0] + GRID_SIZE[0] * CELL_SIZE + INFO_OFFSET + UI_HORIZONTAL_OFFSET) * UI_SCALE, (PLAYGROUND_POS[1] + UI_VERTICAL_OFFSET) * UI_SCALE) self.main_surface.blit(top_headline, top_headline_pos) top = self.font.render(str(self.top).zfill(6), False, TEXT_COLOR) top_pos = ( (PLAYGROUND_POS[0] + GRID_SIZE[0] * CELL_SIZE + INFO_OFFSET + UI_HORIZONTAL_OFFSET) * UI_SCALE, (PLAYGROUND_POS[1] + 0.75 * FONT_SIZE + UI_VERTICAL_OFFSET) * UI_SCALE) self.main_surface.blit(top, top_pos) # Score score_headline = self.font.render("SCORE", False, TEXT_COLOR) score_headline_pos = ( (PLAYGROUND_POS[0] + GRID_SIZE[0] * CELL_SIZE + INFO_OFFSET + UI_HORIZONTAL_OFFSET) * UI_SCALE, (PLAYGROUND_POS[1] + 2.25 * FONT_SIZE + UI_VERTICAL_OFFSET) * UI_SCALE) self.main_surface.blit(score_headline, score_headline_pos) score = self.font.render(str(self.score).zfill(6), False, TEXT_COLOR) score_pos = ((PLAYGROUND_POS[0] + GRID_SIZE[0] * CELL_SIZE + INFO_OFFSET + UI_HORIZONTAL_OFFSET) * UI_SCALE, (PLAYGROUND_POS[1] + 3 * FONT_SIZE + UI_VERTICAL_OFFSET) * UI_SCALE) self.main_surface.blit(score, score_pos) # Lines lines_headline = self.font.render("LINES", False, TEXT_COLOR) lines_headline_pos = ( (PLAYGROUND_POS[0] + GRID_SIZE[0] * CELL_SIZE + INFO_OFFSET + UI_HORIZONTAL_OFFSET) * UI_SCALE, (PLAYGROUND_POS[1] + 4.5 * FONT_SIZE + UI_VERTICAL_OFFSET) * UI_SCALE) self.main_surface.blit(lines_headline, lines_headline_pos) lines = self.font.render(str(self.lines).zfill(6), False, TEXT_COLOR) lines_pos = ( (PLAYGROUND_POS[0] + GRID_SIZE[0] * CELL_SIZE + INFO_OFFSET + UI_HORIZONTAL_OFFSET) * UI_SCALE, (PLAYGROUND_POS[1] + 5.25 * FONT_SIZE + UI_VERTICAL_OFFSET) * UI_SCALE) self.main_surface.blit(lines, lines_pos) # Next next_headline = self.font.render("NEXT", False, TEXT_COLOR) next_headline_pos = ((PLAYGROUND_POS[0] + GRID_SIZE[0] * CELL_SIZE + INFO_OFFSET + UI_HORIZONTAL_OFFSET) * UI_SCALE, (PLAYGROUND_POS[1] + GRID_SIZE[1] * CELL_SIZE - 220 - FONT_SIZE + UI_VERTICAL_OFFSET) * UI_SCALE) self.main_surface.blit(next_headline, next_headline_pos) next_rect = ((PLAYGROUND_POS[0] + GRID_SIZE[0] * CELL_SIZE + UI_HORIZONTAL_OFFSET + INFO_OFFSET) * UI_SCALE, (PLAYGROUND_POS[1] + GRID_SIZE[1] * CELL_SIZE - 220 + UI_VERTICAL_OFFSET) * UI_SCALE, 220 * UI_SCALE, 220 * UI_SCALE) pg.draw.rect(self.main_surface, LINE_COLOR, next_rect, 3) def draw_shapes(self): for rect_x, rect_y in self.cur_shape.get_positions(): self.fill_cell(rect_x, rect_y, self.cur_shape.color) for y in range(GRID_SIZE[1]): for x in range(GRID_SIZE[0]): if self.grid_colliders[x][y]: self.fill_cell(x, y, self.colors[x][y]) # Grid for x in range(1, GRID_SIZE[0]): start_pos = x * CELL_SIZE * UI_SCALE, 0 end_pos = x * CELL_SIZE * UI_SCALE, GRID_SIZE[ 1] * CELL_SIZE * UI_SCALE pg.draw.line(self.playground_surf, tuple(map(lambda c: int(c / 2), LINE_COLOR)), start_pos, end_pos) for y in range(1, GRID_SIZE[1]): start_pos = 0, y * CELL_SIZE * UI_SCALE end_pos = GRID_SIZE[ 0] * CELL_SIZE * UI_SCALE, y * CELL_SIZE * UI_SCALE pg.draw.line(self.playground_surf, tuple(map(lambda c: int(c / 2), LINE_COLOR)), start_pos, end_pos) def draw_next(self): offset_y = -0.5 if int( self.next_shape.shape[0][0]) != self.next_shape.shape[0][0] else 0 for pos in self.next_shape.shape: center_x, center_y = map(lambda s: s / 2 / CELL_SIZE, self.next_surf.get_size()) self.fill_cell(pos[0] + center_x - 0.5, pos[1] + center_y - 0.5 + offset_y, self.next_shape.color, self.next_surf) def fill_cell(self, x, y, color, surface=None): rect = (x * CELL_SIZE * UI_SCALE, y * CELL_SIZE * UI_SCALE, round(CELL_SIZE * UI_SCALE), round(CELL_SIZE * UI_SCALE)) if not surface: pg.draw.rect(self.playground_surf, color, rect) else: pg.draw.rect(surface, color, rect) def check_lines(self): lines = [] for y, *line in enumerate(self.grid_colliders.T): if line[0].all(): lines.append(y) if len(lines): asyncio.run(self.remove_lines(lines)) async def remove_lines(self, lines, color=(0, 255, 0)): self.sound_manager.play(line_effect) half_bright_color = tuple(map(lambda c: int(c / 2), color)) for i in range(5): for y in lines: if i % 2: self.colors[:, y] = [color for _ in range(GRID_SIZE[0])] else: self.colors[:, y] = [ half_bright_color for _ in range(GRID_SIZE[0]) ] self.render() await asyncio.sleep(0.1) for y in lines: self.grid_colliders = np.delete(self.grid_colliders, y, 1) self.grid_colliders = np.insert(self.grid_colliders, 0, 0, 1) self.colors = np.delete(self.colors, y, 1) self.colors = np.insert(self.colors, 0, 0, 1) self.score += 10 * GRID_SIZE[0] self.top = self.score if self.score > self.top else self.top self.lines += 1 self.score += (len(lines) - 1) * 25 def logic(self, time_delta): if not self.game_over: speed_scale = 10 if pg.key.get_pressed()[pg.K_s] else 1 self.cur_shape.update(time_delta * speed_scale) self.check_lines() else: self.restart() def restart(self): pg.mixer.music.rewind() self.score = 0 self.lines = 0 self.colors = np.zeros(GRID_SIZE, dtype=object) self.grid_colliders = np.zeros(GRID_SIZE) self.cur_shape = Shape(self, 5, -1) self.next_shape = Shape(self, 5, -1) self.game_over = False def render(self): self.main_surface.fill(BG_COLOR) self.draw_shapes() self.draw_next() self.draw_surfaces() self.draw_ui() pg.display.update() def mainloop(self): time_delta = 0 while True: start = time() self.check_events() self.logic(time_delta) self.render() time_delta = time() - start