def main(): pygame.mixer.music.play(-1) # 创建主人公飞机 me = myplane.MyPlane(bg_size) # 控制运行的变量 running = True # 设置延迟变量控制飞机两张图片的刷新速度 delay = 60 # 控制切换主人公飞机图片 switch_image = False # 将所有敌人飞机放到一个组里面 enemies = pygame.sprite.Group() # 创建敌人小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) # 创建敌人中型飞机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 5) # 创建敌人大型飞机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) # 创建普通子弹bullet1 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for each in range(BULLET1_NUM): bullet1.append(bullet.Bullte1(me.rect.midtop)) # 创建超级子弹bullet2 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for each in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullte2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullte2((me.rect.centerx + 30, me.rect.centery))) # 创建得分 score = 0 score_font = pygame.font.Font("font/font.ttf", 36) # 标志暂停 paused = False pause_nor_image = pygame.image.load("img/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load( "img/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load("img/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load( "img/resume_pressed.png").convert_alpha() # 四个图片尺寸相同只需要获得一张图rect就行了 paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image # 中弹索引 e1_destory_index = 0 e2_destory_index = 0 e3_destory_index = 0 me_destory_index = 0 # 设置难度级别level level = 1 # 全屏炸弹 bomb_image = pygame.image.load("img/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 # 设置30s一个补给包降落 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) # 设计一个超级子弹double的计时器 DOUBLE_BULLET_TIME = USEREVENT + 1 # 是否使用超级子弹 is_double_bullet = False # 生命数量 life_image = pygame.image.load("img/life.png") life_rect = life_image.get_rect() life_num = 3 # 复活无敌计时器 IMVINCIBLE_TIME = USEREVENT + 2 # 用于组织重复打开记录文件 recorded = False # 绘制结束界面 gameover_font = pygame.font.Font("font/font.ttf", 48) again_image = pygame.image.load("img/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("img/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() clock = pygame.time.Clock() while running: screen.blit(background, (0, 0)) for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 use_bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False # 进行随机生成补给包 elif event.type == SUPPLY_TIME: supply_sound.play() if random.choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == IMVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(IMVINCIBLE_TIME, 0) # 根据用户得分来判断难度级别 if level == 1 and score > 50000: level = 2 upgrade_sound.play() # 增加三架小型飞机,两架中型飞机,一架大型飞机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) inc_speed(small_enemies, 1) elif level == 2 and score > 300000: level = 3 upgrade_sound.play() # 增加三架小型飞机,两架中型飞机,一架大型飞机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 3 and score > 600000: level = 4 upgrade_sound.play() # 增加五架小型飞机,三架中型飞机,二架大型飞机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 4 and score > 1000000: upgrade_sound.play() # 增加五架小型飞机,三架中型飞机,二架大型飞机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) # 判断是否暂停游戏 if life_num and not paused: ##########检测用户键盘操作########## key_pressed = pygame.key.get_pressed() # 根据键盘方向判断飞机的移动 if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() ##########检测用户键盘操作########## #绘制补给并进行二者碰撞检测 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False # 发射子弹 if not (delay % 10): button_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM # 检测子弹是否击中敌机 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False # 绘制分数 score_text = score_font.render("Score : %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) ###################把飞机图像画到画布上###################### # 生成大型飞机 for each in big_enemies: if each.active: each.move() # 绘制被打到的特效 if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5),\ 2) # 当生命大于20%时显示绿色,反之显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), \ 2) # 如果即将出现则播放大型飞机专属bgm if each.rect.bottom == -50: enemy3_flying_sound.play(-1) else: # 毁灭 if (delay % 3): if e3_destory_index == 0: enemy3_down_sound.play() screen.blit(each.destory_images[e3_destory_index], each.rect) e3_destory_index = (e3_destory_index + 1) % 6 if e3_destory_index == 0: enemy3_flying_sound.stop() score += 10000 each.reset() # 生成中型飞机 for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # 当生命大于20%时显示绿色,反之显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), \ 2) else: # 毁灭 if (delay % 3): if e2_destory_index == 0: enemy2_down_sound.play() screen.blit(each.destory_images[e2_destory_index], each.rect) e2_destory_index = (e2_destory_index + 1) % 4 if e2_destory_index == 0: score += 6000 each.reset() # 生成小型飞机 for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: # 毁灭 if (delay % 3): if e1_destory_index == 0: enemy1_down_sound.play() screen.blit(each.destory_images[e1_destory_index], each.rect) e1_destory_index = (e1_destory_index + 1) % 4 if e1_destory_index == 0: score += 1000 each.reset() # 生成主角驾驶的飞机 #检测我方飞机是否被撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and me.invincible: me.active = True elif enemies_down: me.active = False for e in enemies_down: e.active = False if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: # 毁灭 if (delay % 3): if me_destory_index == 0: me_down_sound.play() screen.blit(me.destory_images[me_destory_index], me.rect) me_destory_index = (me_destory_index + 1) % 4 if me_destory_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(IMVINCIBLE_TIME, 3 * 1000) # 绘制炸弹: bomb_text = bomb_font.render("x %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # 绘制飞机生命数量 if life_num: for each in range(life_num): screen.blit(life_image, \ (width - 10 - (each + 1)*life_rect.width, \ height - 10 - life_rect.height)) # 绘制游戏失败 elif life_num == 0: # 背景音乐停止 pygame.mixer.music.stop() # 停止全部音效 pygame.mixer.stop() # 停止发放补给 pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: # 读取记录文件 recorded = True with open("recoder.txt", "r") as f: record_score = int(f.read()) # 如果分数是最高分则记录 if score > record_score: with open("recoder.txt", "w") as f: f.write(str(score)) # 绘制结束画面 record_score_text = score_font.render("Best : %d" % record_score, True, (255, 255, 255)) screen.blit(record_score_text, (50, 50)) gameover_text1 = gameover_font.render("Your Score", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = \ (width - again_rect.width) // 2, \ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) # 检测用户的鼠标操作 # 如果用户按下鼠标左键 if pygame.mouse.get_pressed()[0]: # 获取鼠标坐标 pos = pygame.mouse.get_pos() # 如果用户点击“重新开始” if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: # 调用main函数,重新开始游戏 main() # 如果用户点击“结束游戏” elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: # 退出游戏 pygame.quit() sys.exit() #绘制暂停按钮 screen.blit(paused_image, paused_rect) if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 60 ###################把飞机图像画到画布上###################### pygame.display.flip() clock.tick(60)
def run(): pygame.mixer.music.play(-1) # 生成我方飞机 me = myplane.MyPlane(bg_size) enemies = pygame.sprite.Group() # 生成敌方小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) # 生成敌方中型飞机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) # 生成敌方大型飞机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) # 生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # 生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM//2): bullet2.append(bullet.Bullet2((me.rect.centerx-33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx+30, me.rect.centery))) clock = pygame.time.Clock() # 中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 # 统计得分 score = 0 score_font = pygame.font.Font("font/font.ttf", 36) # 标志是否暂停游戏 paused = False pause_nor_image = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load("images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load("images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load("images/resume_pressed.png").convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image # 设置难度级别 level = 1 # 全屏炸弹 bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 # 每30秒发放一个补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) # 超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 # 标志是否使用超级子弹 is_double_bullet = False # 解除我方无敌状态定时器 INVINCIBLE_TIME = USEREVENT + 2 # 生命数量 life_image = pygame.image.load("images/life.png").convert_alpha() life_rect = life_image.get_rect() life_num = 300 # 用于阻止重复打开记录文件 recorded = False # 游戏结束画面 gameover_font = pygame.font.Font("font/font.ttf", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() # 用于切换图片 switch_image = True # 用于延迟 delay = 100 running = True while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() trigger_server.conn.close()#设置socket断开 sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) # 根据用户的得分增加难度 if level == 1 and score > 50000: level = 2 upgrade_sound.play() # 增加3架小型敌机、2架中型敌机和1架大型敌机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) # 提升小型敌机的速度 inc_speed(small_enemies, 1) elif level == 2 and score > 300000: level = 3 upgrade_sound.play() # 增加5架小型敌机、3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升小型敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 3 and score > 600000: level = 4 upgrade_sound.play() # 增加5架小型敌机、3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升小型敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 4 and score > 1000000: level = 5 upgrade_sound.play() # 增加5架小型敌机、3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升小型敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) screen.blit(background, (0, 0)) if life_num and not paused: # 检测用户的键盘操作和肌电识别程序传来的trigger key_pressed = pygame.key.get_pressed() trigger = trigger_server.get_trigger() #print(trigger) if key_pressed[K_w] or key_pressed[K_UP] or trigger == T_UP: me.moveUp(SPEED) if key_pressed[K_s] or key_pressed[K_DOWN] or trigger == T_DOWN: me.moveDown(SPEED) if key_pressed[K_a] or key_pressed[K_LEFT] or trigger == T_LEFT: me.moveLeft(SPEED) if key_pressed[K_d] or key_pressed[K_RIGHT] or trigger == T_RIGHT: me.moveRight(SPEED) # 避免飞机向一个方向飞到底,及时将trigger置零 trigger_server.set_trigger(NONE) # 绘制全屏炸弹补给并检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False # 绘制超级子弹补给并检测是否获得 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False # 发射子弹 if not(delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset((me.rect.centerx-33, me.rect.centery)) bullets[bullet2_index+1].reset((me.rect.centerx+30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM # 检测子弹是否击中敌机 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide(b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False # 绘制大型敌机 for each in big_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # 当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) # 即将出现在画面中,播放音效 if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: # 毁灭 if not(delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 each.reset() # 绘制中型敌机: for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # 当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) else: # 毁灭 if not(delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 each.reset() # 绘制小型敌机: for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: # 毁灭 if not(delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() # 检测我方飞机是否被撞 enemies_down = pygame.sprite.spritecollide(me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False # 绘制我方飞机 if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: # 毁灭 if not(delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) # 绘制全屏炸弹数量 bomb_text = bomb_font.render("× %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # 绘制剩余生命数量 if life_num: for i in range(life_num): screen.blit(life_image, \ (width-10-(i+1)*life_rect.width, \ height-10-life_rect.height)) # 绘制得分 score_text = score_font.render("Score : %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) # 绘制游戏结束画面 elif life_num == 0: # 背景音乐停止 pygame.mixer.music.stop() # 停止全部音效 pygame.mixer.stop() # 停止发放补给 pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True # 读取历史最高得分 with open("record.txt", "r") as f: record_score = int(f.read()) # 如果玩家得分高于历史最高得分,则存档 if score > record_score: with open("record.txt", "w") as f: f.write(str(score)) # 绘制结束画面 record_score_text = score_font.render("Best : %d" % record_score, True, (255, 255, 255)) screen.blit(record_score_text, (50, 50)) gameover_text1 = gameover_font.render("Your Score", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = \ (width - again_rect.width) // 2, \ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) # 检测用户的鼠标操作 # 如果用户按下鼠标左键 if pygame.mouse.get_pressed()[0]: # 获取鼠标坐标 pos = pygame.mouse.get_pos() # 如果用户点击“重新开始” if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: # 调用main函数,重新开始游戏 main() # 如果用户点击“结束游戏” elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: # 退出游戏 pygame.quit() trigger_server.conn.close()#设置socket断开 sys.exit() # 绘制暂停按钮 screen.blit(paused_image, paused_rect) # 切换图片 if not(delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) clock = pygame.time.Clock() # 中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 me = myplane.MyPlane(bg_size) enemies = pygame.sprite.Group() # 生成敌方小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 5) big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 1) running = True switch_image = True delay = 100 score = 0 score_font = pygame.font.Font("font/font.ttf", 36) bullets = [] # 生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # 生命数量 life_image = pygame.image.load("images/life.png").convert_alpha() life_rect = life_image.get_rect() life_num = 3 # 游戏结束画面 gameover_font = pygame.font.Font("font/font.ttf", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() DOUBLE_BULLET_TIME = USEREVENT + 1 # 解除我方飞机无敌状态 INVINCEBLE_TIME = USEREVENT + 2 # 生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) # 标记是否使用超级子弹 is_double_bullet = False level = 1 # 全屏炸弹 bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 # 每30秒发放一个补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) # 阻止重复读取成绩记录文件 recorded = False # 标志是否暂停游戏 paused = False ####################### stopping_img = pygame.image.load("images/stopping.png").convert_alpha() stopping_rect = stopping_img.get_rect() stopping_rect.left, stopping_rect.top = width / 2 - stopping_rect.width / 2, height / 2 - stopping_rect.height / 2 ######################### paused_nor_image = pygame.image.load( "images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load( "images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load( "images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load( "images/resume_pressed.png").convert_alpha() paused_rect = paused_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = paused_nor_image while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() paused_image = resume_pressed_image else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() paused_image = pause_pressed_image elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = paused_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCEBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCEBLE_TIME, 0) # 根据用户的得分增加难度 if level == 1 and score > 30000: level = 2 upgrade_sound.play() add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) inc_speed(small_enemies, 1) elif level == 2 and score > 100000: level = 3 upgrade_sound.play() add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 3 and score > 500000: level = 4 upgrade_sound.play() add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 4 and score > 1000000: level = 5 upgrade_sound.play() add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) screen.blit(background, (0, 0)) if life_num and not paused: # 绘制全屏炸弹补给并检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False # 发射子弹 if not (delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 33, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM # 检测子弹是否击中敌机 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False # 绘制全屏炸弹补给并检测是否获得 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False # 绘制大型敌机 for each in big_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) if each.rect.bottom == -50: enemy3_fly_sound.play(-1) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), \ 2) else: if not (delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: me_down_sound.stop() score += 10000 each.reset() # 绘制中型敌机 for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image1, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), \ 2) else: if not (delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 5000 each.reset() # 绘制小型敌机 for each in small_enemies: if each.active: each.move() screen.blit(each.image1, each.rect) else: if not (delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() # 检测我方飞机是否被撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False # 绘制我方飞机 if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: me_down_sound.play() if not (delay % 3): screen.blit(each.destroy_images[me_destroy_index], each.rect) me_destroy_index = (me_destroy_index + 1) % 4 # 剩余生命数量 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCEBLE_TIME, 3 * 1000) # 绘制剩余炸弹数量 bomb_text = bomb_font.render("x %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) if life_num: for i in range(life_num): screen.blit(life_image, \ (width - 10 - (i + 1) * life_rect.width, \ height - 10 - life_rect.height)) score_text = score_font.render(str("Score: %s" % score), True, WHITE) screen.blit(score_text, (10, 5)) elif life_num == 0: pygame.mixer.music.stop() pygame.mixer.stop() # 停止发放补给 pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True # 读取历史最高分 ################################################# ################################################# with open("record.txt", "r") as f: record_score = int(f.read()) with open("recordname.txt", "r") as f: record_name = str(f.read()) if score > record_score: with open("record.txt", "w") as f: f.write(str(score)) with open("records.txt", "r") as f: record_bestname = str(f.read()) with open("recordname.txt", "w") as f: f.write(str(record_bestname)) # 绘制结束画面 record_score_text = score_font.render( "Best: %d User_Name:%s" % (record_score, record_name), True, WHITE) screen.blit(record_score_text, (50, 50)) gameover_text1 = gameover_font.render("Your Score: ", True, WHITE) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 2 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, WHITE) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = \ (width - again_rect.width) // 2, \ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) # 检测用户的鼠标操作 # 如果用户按下鼠标左键 if pygame.mouse.get_pressed()[0]: pos = pygame.mouse.get_pos() if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: main() elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: pygame.quit() sys.exit() screen.blit(paused_image, paused_rect) # 切换图片 if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer_music.play(-1) #生成我方飞机 me = myplane.MyPlane(bg_size) #生成敌方飞机,大。中。小共三类 enemies = pygame.sprite.Group() small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) #生成子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) clock = pygame.time.Clock() #中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 #统计用户得分 score = 0 score_font = pygame.font.Font("font/font.ttf", 36) # 全屏炸弹 bomb_image = pygame.image.load('images/bomb.png').convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 # 生成补给 bomb_supply = supply.Bomb_Supply(bg_size) #用于切换图片 switch_image = True #生命数量 life_num = 1 # 游戏结束画面 gameover_font = pygame.font.Font("font/font.TTF", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() #用于延迟 delay = 100 running = True while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False screen.blit(background, (0, 0)) #检测用户键盘操作 key_pressed = pygame.key.get_pressed() if life_num: key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() # 绘制全屏炸弹补给 bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) screen.blit(background, (0, 0)) #发射子弹 if not (delay % 10): bullet_sound.play() bullet1[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM #检测子弹是否击中敌机 for b in bullet1: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False #绘制敌方大型飞机 for each in big_enemies: if each.active: each.move() if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) #绘制血槽 pygame.draw.line(screen,BLACK,\ (each.rect.left,each.rect.top - 5),\ (each.rect.right,each.rect.top - 5),\ 2) #当生命值大于20%,血条现实绿色,否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen,energy_color,\ (each.rect.left,each.rect.top - 5),\ (each.rect.left + each.rect.width * energy_remain,\ each.rect.top - 5),\ 2 ) # 当大型飞机出现之前,播放音效 if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: #飞机损毁 if not (delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 each.reset() # 绘制敌方中型飞机 for each in mid_enemies: if each.active: each.move() screen.blit(each.image, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # 当生命值大于20%,血条现实绿色,否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), \ 2 ) else: #敌方中型飞机毁灭 if not (delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 each.reset() # 绘制敌方小型飞机 for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: #敌方小型飞机毁灭 if not (delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() #检测飞机是否被碰撞 enemy_down = pygame.sprite.spritecollide(me, enemies, False) if enemy_down: me.active = False for e in enemy_down: e.active = False #绘制我的飞机 if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: #我方飞机毁灭 if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num = 0 me.reset() # 绘制全屏炸弹数量 bomb_text = bomb_font.render("× %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) #绘制得分 score_text = score_font.render("Score : %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) # 绘制结束界面 if life_num == 0: # 背景音乐停止 pygame.mixer.music.stop() # 停止全部音效 pygame.mixer.stop() gameover_text1 = gameover_font.render("Your Score", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) #切换图片,60帧,一秒切换12次 if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) score = 0 level = 1 score_font = pygame.font.Font("font/font.ttf", 36) #全屏炸弹 bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 #每30s生成一个补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 10 * 1000) #超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 is_double_bullet = False #设置生命次数 life_num = 3 life_image = pygame.image.load("images/life.png") life_rect = life_image.get_rect() #标志是否暂停游戏 paused = False pause_nor_image = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load( "images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load( "images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load( "images/resume_pressed.png").convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 pause_image = pause_nor_image # 重新开始结束游戏 again = pygame.image.load("images/again.png").convert_alpha() gameover = pygame.image.load("images/gameover.png").convert_alpha() again_rect = again.get_rect() gameover_rect = gameover.get_rect() #生成我方飞机 me = myplant.Myplane(bg_size) #切换飞机图片 transPlane = True #延迟变量 delay = 100 #生成敌机 enemies = pygame.sprite.Group() #摧毁图片索引 small_destroy = 0 mid_destroy = 0 big_destroy = 0 my_destroy = 0 small_enenmies = pygame.sprite.Group() add_small_enemies(small_enenmies, enemies, 15) mid_enenmies = pygame.sprite.Group() add_mid_enemies(mid_enenmies, enemies, 4) big_enenmies = pygame.sprite.Group() add_big_enemies(big_enenmies, enemies, 1) #生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # 生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) clock = pygame.time.Clock() running = True while running: for event in pygame.event.get(): if event.type == pygame.QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: # 重新开始 结束游戏 if event.button == 1 and gameover_rect.collidepoint(event.pos): pygame.quit() sys.exit() if event.button == 1 and again_rect.collidepoint(event.pos): main() if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: pause_image = resume_pressed_image else: pause_image = pause_pressed_image else: if paused: pause_image = resume_nor_image else: pause_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: if randint(0, 2): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) #根据用户得分增加难度 if level == 1 and score > 50000: level = 2 #增加3小2中1大 add_small_enemies(small_enenmies, enemies, 3) add_mid_enemies(mid_enenmies, enemies, 2) add_big_enemies(big_enenmies, enemies, 1) #提升小型速度 inc_speed(small_enenmies, 1) elif level == 2 and score > 200000: level = 3 #增加3小2中1大 add_small_enemies(small_enenmies, enemies, 5) add_mid_enemies(mid_enenmies, enemies, 3) add_big_enemies(big_enenmies, enemies, 2) #提升小型速度 inc_speed(small_enenmies, 1) inc_speed(mid_enenmies, 1) elif level == 3 and score > 600000: level = 4 #增加3小2中1大 add_small_enemies(small_enenmies, enemies, 5) add_mid_enemies(mid_enenmies, enemies, 3) add_big_enemies(big_enenmies, enemies, 2) #提升小型速度 inc_speed(small_enenmies, 1) inc_speed(mid_enenmies, 1) elif level == 4 and score > 1000000: level = 5 #增加3小2中1大 add_small_enemies(small_enenmies, enemies, 5) add_mid_enemies(mid_enenmies, enemies, 3) add_big_enemies(big_enenmies, enemies, 2) #提升小型速度 inc_speed(small_enenmies, 1) inc_speed(mid_enenmies, 1) screen.blit(background, (0, 0)) #游戏动态程序 if paused or life_num == 0: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() screen.blit(again, ((width - again_rect.width) // 2, height // 2 - 20)) screen.blit(gameover, ((width - gameover_rect.width) // 2, height // 2 + 20)) else: # 检测键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() #绘制全屏炸弹并检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): bomb_num += 1 bomb_supply.active = False if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 10 * 1000) bullet_supply.active = False #绘制大型敌机 for each in big_enenmies: if each.active: each.move() if transPlane and (delay % 5 == 0): screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) #绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) #当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.bigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line( screen, energy_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) else: #毁灭 if not (delay % 3): screen.blit(each.destroy_images[big_destroy], each.rect) big_destroy = (big_destroy + 1) % 6 if big_destroy == 0: each.reset() score += 10000 #绘制中小型机 for each in mid_enenmies: if each.active: each.move() screen.blit(each.image, each.rect) pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) # 当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.midEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line( screen, energy_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) else: if not (delay % 3): screen.blit(each.destroy_images[mid_destroy], each.rect) mid_destroy = (mid_destroy + 1) % 4 if mid_destroy == 0: each.reset() score += 6000 for each in small_enenmies: if each.active: each.move() screen.blit(each.image, each.rect) else: if not (delay % 3): screen.blit(each.destroy_images[small_destroy], each.rect) small_destroy = (small_destroy + 1) % 4 if small_destroy == 0: each.reset() score += 1000 #检测我方飞机是否被撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down: me.active = False for e in enemies_down: e.active = False #绘制我方飞机 if me.active: transPlane = not transPlane if transPlane and (delay % 5 == 0): screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: if not (delay % 3): screen.blit(me.destroy_images[my_destroy], me.rect) my_destroy = (my_destroy + 1) % 4 if my_destroy == 0: life_num -= 1 me.reset() #绘制子弹 if not (delay % 10): if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM #发射子弹检测是否击中敌机 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e not in small_enenmies: screen.blit(e.image_hit, e.rect) e.energy -= 1 if e.energy == 0: e.active = False delay -= 1 if not delay: delay = 100 screen.blit(pause_image, paused_rect) score_text = score_font.render("Score : %s" % str(score), True, BLACK) screen.blit(score_text, (10, 5)) # 绘制炸弹数量 bomb_text = bomb_font.render(" * %d" % bomb_num, True, RED) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # 绘制生命次数 life_text = score_font.render("* %d" % life_num, True, RED) life_text_rect = life_text.get_rect() screen.blit(life_image, (width - life_text_rect.width - 30 - life_rect.width, height - 5 - life_rect.height)) screen.blit(life_text, (width - life_text_rect.width - 20, height - 5 - life_text_rect.height)) pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1)#播放背景音乐 me=myplane.MyPlane(bg_size)#生成我方飞机 enemies=pygame.sprite.Group()#生成敌方飞机 small_enemies=pygame.sprite.Group()#生成小型飞机 add_small_enemies(small_enemies,enemies,15) mid_enemies = pygame.sprite.Group() # 生成中型飞机 add_mid_enemies(mid_enemies, enemies, 4) big_enemies = pygame.sprite.Group() # 生成大型飞机 add_big_enemies(big_enemies, enemies, 4) bullet1=[]#生成普通子弹 bullet1_index=0 bullet1_NUM=4#四颗子弹 for i in range(bullet1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop))#顶部中央生成子弹 bullet2 = [] # 生成超级子弹 bullet2_index = 0 bullet2_NUM = 8 # 8颗子弹 for i in range(bullet2_NUM//2): bullet2.append(bullet.Bullet2((me.rect.centerx-33,me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx+30,me.rect.centery)))#从炮筒射击 clock=pygame.time.Clock() e1_destroy_index=0#中弹图片索引 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 score=0#统计得分 score_font=pygame.font.Font("font/font.ttf",36)#加载36号字体 paused=False#暂停标志 paused_nor_image=pygame.image.load("images/pause_nor.png").convert_alpha() paused_pressed_image=pygame.image.load("images/pause_pressed.png").convert_alpha() resume_nor_image=pygame.image.load("images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load("images/resume_pressed.png").convert_alpha() paused_rect=paused_nor_image.get_rect() paused_rect.left,paused_rect.top=width-paused_rect.width-10,10#右上角显示 paused_image=paused_nor_image level=1 bomb_image=pygame.image.load("images/bomb.png").convert_alpha()#全屏炸弹 bomb_rect=bomb_image.get_rect() bomb_font=pygame.font.Font("font/font.ttf",48)#48号字体 bomb_num=3 bullet_supply=supply.Bullet_Supply(bg_size)#每30秒发放一个补给包 bomb_supply=supply.Bomb_Supply(bg_size)#实例化 SUPPLY_TIME=USEREVENT#自定义事件 pygame.time.set_timer(SUPPLY_TIME,30*1000)#30秒 DOUBLE_BULLET_TIEM=USEREVENT+1#超级子弹定时器 is_double_bullet=False#标志是否使用超级子弹 INVINCIBLE_TIME=USEREVENT+2#解除我方无敌状态计时器 life_image=pygame.image.load("images/life.png").convert_alpha() life_rect=life_image.get_rect() life_num=3#生命数量 recorded=False#防止重复打开文件 gameover_font=pygame.font.Font("font/font.ttf",48)#游戏结束画面 again_image=pygame.image.load("images/again.png").convert_alpha() again_rect=again_image.get_rect() gameover_image=pygame.image.load("images/gameover.png").convert_alpha() gameover_rect=gameover_image.get_rect() switch_image=True#用于切换me1.png和me2.png delay=100#用于延迟 running=True while running: for event in pygame.event.get(): if event.type==QUIT:#退出 pygame.quit() sys.exit() elif event.type==MOUSEBUTTONDOWN: if event.button==1 and paused_rect.collidepoint(event.pos):#检测点是否在矩形中 paused=not paused if paused: pygame.time.set_timer(SUPPLY_TIME,0)#取消自定义事件(补给) pygame.mixer.music.pause()#暂停音乐 pygame.mixer.pause()#暂停音效 else: pygame.time.set_timer(SUPPLY_TIME,30*1000)#自定义事件 pygame.mixer.music.unpause()#恢复音乐 pygame.mixer.unpause()#恢复音效 elif event.type==MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image=resume_pressed_image else: paused_image=paused_pressed_image else: if paused: paused_image=resume_nor_image else: paused_image=paused_nor_image elif event.type==KEYDOWN: if event.key==K_SPACE:#按下空格用炸弹 if bomb_num: bomb_num-=1 bomb_sound.play() for each in enemies: if each.rect.bottom>0: each.active=False elif event.type==SUPPLY_TIME:#响应事件 supply_sound.play() if choice([True,False]):#在true和false中选择一个 bomb_supply.reset() else: bullet_supply.reset() elif event.type==DOUBLE_BULLET_TIEM: is_double_bullet=False pygame.time.set_timer(DOUBLE_BULLET_TIEM,0)#取消定时器 elif event.type==INVINCIBLE_TIME: me.invincible=False pygame.time.set_timer(INVINCIBLE_TIME,0)#解除无敌 if level==1 and score>30: level=2#根据得分增加难度 upgrade_sound.play() add_small_enemies(small_enemies,enemies,4)#增加4架小敌机 add_mid_enemies(mid_enemies,enemies,3)#增加3架中敌机 add_big_enemies(big_enemies,enemies,1)#增加一架大敌机 inc_speed(small_enemies,2)#提升小敌机的速度 elif level==2 and score>100: level=3#根据得分增加难度 upgrade_sound.play() add_small_enemies(small_enemies,enemies,5)#增加5架小敌机 add_mid_enemies(mid_enemies,enemies,4)#增加4架中敌机 add_big_enemies(big_enemies,enemies,2)#增加2架大敌机 inc_speed(small_enemies,2)#提升小敌机的速度 inc_speed(mid_enemies, 2) # 提升中敌机的速度 elif level==3 and score>300: level=4#根据得分增加难度 upgrade_sound.play() add_small_enemies(small_enemies,enemies,6)#增加6架小敌机 add_mid_enemies(mid_enemies,enemies,5)#增加5架中敌机 add_big_enemies(big_enemies,enemies,3)#增加3架大敌机 inc_speed(small_enemies,2)#提升小敌机的速度 inc_speed(mid_enemies, 2) # 提升中敌机的速度 inc_speed(big_enemies, 2) # 提升大敌机的速度 screen.blit(background, (0, 0)) if life_num and not paused: key_pressed=pygame.key.get_pressed()#检测键盘按下操作 if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() if bomb_supply.active:#绘制全屏炸弹并检测是否获得 bomb_supply.move() screen.blit(bomb_supply.image,bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply,me):#检测碰撞 get_bomb_sound.play() if bomb_num<3: bomb_num+=1 bomb_supply.active=False if bullet_supply.active:#绘制超级子弹并检测是否获得 bullet_supply.move() screen.blit(bullet_supply.image,bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply,me):#检测碰撞 get_bullet_sound.play() is_double_bullet=True#发射超级子弹 pygame.time.set_timer(DOUBLE_BULLET_TIEM,18*1000)#18秒的使用时间 bullet_supply.active=False if not (delay%10): bullet_sound.play() if is_double_bullet: bullets=bullet2 bullets[bullet2_index].reset((me.rect.centerx-33,me.rect.centery))#发射子弹 bullets[bullet2_index+1].reset((me.rect.centerx+30,me.rect.centery)) bullet2_index = (bullet2_index + 2) % bullet2_NUM # 指向下一个索引,不能超过8 else: bullets=bullet1 bullets[bullet1_index].reset(me.rect.midtop)#发射子弹 bullet1_index=(bullet1_index+1)%bullet1_NUM#指向下一个索引,不能超过4 for b in bullets:#检测子弹是否击中 if b.active: b.move() screen.blit(b.image,b.rect) enemy_hit=pygame.sprite.spritecollide(b,enemies,False,pygame.sprite.collide_mask)#被子弹打中的敌机 if enemy_hit: b.active=False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit=True e.energy-=1#每次击中减1点血 if e.energy==0: e.active=False else: e.active=False for each in big_enemies: if each.active: each.move() if each.hit:#绘制被打到的特效 screen.blit(each.image_hit,each.rect) each.hit=False else: if switch_image:#绘制大型敌机 screen.blit(each.image1,each.rect) else: screen.blit(each.image2,each.rect) pygame.draw.line(screen,BLACK,(each.rect.left,each.rect.top-5),(each.rect.right,each.rect.top-5),2)#绘制血槽 energy_remain=each.energy/enemy.BigEnemy.energy if energy_remain>0.2:#如果生命大于20%显示绿色,否则显示红色 enemies_color=GREEN else: enemies_color=RED pygame.draw.line(screen,enemies_color,(each.rect.left,each.rect.top-5),(each.rect.left+each.rect.width*energy_remain,each.rect.top-5),2) if each.rect.bottom==-50:#即将出现播放音乐 enemy3_fly_sound.play(-1) else: if not(delay%3): if e3_destroy_index == 0: enemy3_down_sound.play()#播放毁灭音效 screen.blit(each.destroy_images[e3_destroy_index],each.rect) e3_destroy_index=(e3_destroy_index+1)%6#依次播放毁灭画面 if e3_destroy_index==0: enemy3_fly_sound.stop() score+=100 each.reset() for each in mid_enemies: if each.active: each.move()#绘制中型敌机 if each.hit: screen.blit(each.image_hit,each.rect) each.hit=False else: screen.blit(each.image,each.rect) pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) # 绘制血槽 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: # 如果生命大于20%显示绿色,否则显示红色 enemies_color = GREEN else: enemies_color = RED pygame.draw.line(screen, enemies_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) else: if not(delay%3): if e2_destroy_index == 0: enemy2_down_sound.play()#播放毁灭音效 screen.blit(each.destroy_images[e2_destroy_index],each.rect) e2_destroy_index=(e2_destroy_index+1)%4#依次播放毁灭画面 if e2_destroy_index==0: score+=10 each.reset() for each in small_enemies: if each.active: each.move()#绘制小型敌机 screen.blit(each.image,each.rect) else: if not(delay%3): if e1_destroy_index == 0: enemy1_down_sound.play()#播放毁灭音效 screen.blit(each.destroy_images[e1_destroy_index],each.rect) e1_destroy_index=(e1_destroy_index+1)%4#依次播放毁灭画面 if e1_destroy_index==0: score+=1 each.reset() enemies_down=pygame.sprite.spritecollide(me,enemies,False,pygame.sprite.collide_mask)#检测碰撞 if enemies_down and not me.invincible: me.active=False#飞机毁灭 for e in enemies_down: e.active=False if me.active: if switch_image: screen.blit(me.image1,me.rect)#绘制我方飞机 else: screen.blit(me.image2,me.rect) else: if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() # 播放毁灭音效 screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 # 依次播放毁灭画面 if me_destroy_index == 0: life_num-=1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME,3*1000)#3秒无敌 bomb_text=bomb_font.render("*%d"%bomb_num,True,WHITE)#绘制炸弹数量 text_rect=bomb_text.get_rect() screen.blit(bomb_image,(10,height-10-bomb_rect.height)) screen.blit(bomb_text,(20+bomb_rect.width,height-5-text_rect.height)) if life_num:#绘制剩余生命数量 for i in range(life_num): screen.blit(life_image,(width-10-(i+1)*life_rect.width,height-10-life_rect.height)) score_text = score_font.render("Score:%s" % str(score), True, WHITE) # 白色分数,无抗锯齿 screen.blit(score_text, (10, 5)) # 绘制得分 elif life_num==0:#绘制游戏结束画面 pygame.mixer.music.stop()#背景音乐停止 pygame.mixer.stop()#停止全部音效 pygame.time.set_timer(SUPPLY_TIME,0)#停止发放补给 if not recorded: recorded=True with open("record.txt","r") as f: record_score=int(f.read())#读取历史最高分 if score>record_score: with open("record.txt","w") as f: f.write(str(score))#如果高于历史最高分,则存档 record_score_text = score_font.render("Best: %d" % record_score, True, WHITE)# 绘制结束画面 screen.blit(record_score_text, (10, 5)) gameover_text1 = gameover_font.render("Your Score: ", True, WHITE) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = (width - gameover_text1_rect.width) // 2, height // 2 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, WHITE) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = (width - gameover_text2_rect.width) // 2,gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = (width - again_rect.width) // 2, gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = (width - again_rect.width) // 2,again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) if pygame.mouse.get_pressed()[0]:# 检测用户的鼠标操作 pos = pygame.mouse.get_pos()# 如果用户按下鼠标左键 if again_rect.left < pos[0] < again_rect.right and again_rect.top < pos[1] < again_rect.bottom: main() elif gameover_rect.left < pos[0] < gameover_rect.right and gameover_rect.top < pos[1] < gameover_rect.bottom: pygame.quit() sys.exit() screen.blit(paused_image,paused_rect)#绘制暂停图片 if not (delay%5):#切换图片 switch_image=not switch_image delay-=1 if not delay: delay=100 pygame.display.flip() clock.tick(60)#60帧
def main(): pygame.mixer.music.play(-1) #播放背景音乐 me = myplane.MyPlane(bg_size) #生成我方飞机 enemies = pygame.sprite.Group() #敌方机组 #生成小型敌机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies,enemies,15) #生成中型敌机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies,enemies,4) #生成大型敌机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies,enemies,2) #生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) #实例化子弹,生成在图片顶部中间 #生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM//2): bullet2.append(bullet.Bullet2((me.rect.centerx-33,me.rect.centery)))#实例化子弹,生成在图片顶部中间 bullet2.append(bullet.Bullet2((me.rect.centerx+30,me.rect.centery))) clock = pygame.time.Clock() running = True #用于主循环 switch_image = True #用于切换图片 delay = 100 #用于延迟 #中弹索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 #统计分数 score = 0 score_font = pygame.font.Font("font/font.ttf",36) #定义字体 #标记是否暂停游戏 paused = False paused_nor_image = pygame.image.load("images\\pause_nor.png").convert_alpha() paused_pressed_image = pygame.image.load("images\\pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load("images\\resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load("images\\resume_pressed.png").convert_alpha() paused_rect = paused_nor_image.get_rect() paused_rect.left,paused_rect.top = width - paused_rect.width - 10 ,10 #设置暂停按钮位置 paused_image = paused_nor_image #游戏结束画面 gameover_font = pygame.font.Font("font\\font.ttf",48) again_image = pygame.image.load("images\\again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images\\gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() #设置游戏级别 level = 1 #炸弹 bomb_image = pygame.image.load("images\\bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font\\font.ttf",48) bomb_num = 3 #每30秒发放一个补给包,实例化子弹与炸弹 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME,30 * 1000) #超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 #标记是否使用超级子弹 is_double_bullet = False #解除我方飞机重生保护状态 INVINCIBLE_TIME = USEREVENT + 2 #我方飞机生命数量 life_image = pygame.image.load("images\\life.png").convert_alpha() life_rect = life_image.get_rect() life_num = 3 #用于阻止重复打开记录文件record.txt recorded = False #用于结束游戏是隐藏暂停按钮 BUTTON_ON = True #--------循环主体--------------- while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() #判断暂停按钮与继续按钮进行切换 elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused #暂停时音效暂停播放 if paused: pygame.time.set_timer(SUPPLY_TIME,0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME,3 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = paused_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = paused_nor_image #按下空格释放炸弹,数量递减 播放音效 销毁飞机 elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True,False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type ==DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME,0) #关闭定时器 elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME,0) #根据得分更改游戏等级 if level == 1 and score > 5000: level = 2 upgrade_sound.play() #增加3架小型敌机,2架中型敌机和1架大型敌机 add_small_enemies(small_enemies,enemies,3) add_mid_enemies(mid_enemies,enemies,2) add_big_enemies(big_enemies,enemies,1) #提升小型敌机速度 inc_speed(small_enemies,1) elif level == 2 and score > 300000: level = 3 upgrade_sound.play() #增加5架小型敌机,3架中型敌机和2架大型敌机 add_small_enemies(small_enemies,enemies,5) add_mid_enemies(mid_enemies,enemies,3) add_big_enemies(big_enemies,enemies,2) #提升敌机速度 inc_speed(small_enemies,1) inc_speed(mid_enemies,1) elif level == 3 and score > 600000: level = 4 upgrade_sound.play() #增加5架小型敌机,3架中型敌机和2架大型敌机 add_small_enemies(small_enemies,enemies,5) add_mid_enemies(mid_enemies,enemies,3) add_big_enemies(big_enemies,enemies,2) #提升敌机速度 inc_speed(small_enemies,1) inc_speed(mid_enemies,1) elif level == 4 and score > 1000000: level = 5 upgrade_sound.play() #增加5架小型敌机,3架中型敌机和2架大型敌机 add_small_enemies(small_enemies,enemies,5) add_mid_enemies(mid_enemies,enemies,3) add_big_enemies(big_enemies,enemies,2) #提升敌机速度 inc_speed(small_enemies,1) inc_speed(mid_enemies,1) elif level == 5 and score > 5000000: level = 5 upgrade_sound.play() #增加5架小型敌机,3架中型敌机和2架大型敌机 add_small_enemies(small_enemies,enemies,5) add_mid_enemies(mid_enemies,enemies,3) add_big_enemies(big_enemies,enemies,2) #提升敌机速度 inc_speed(small_enemies,1) inc_speed(mid_enemies,1) screen.blit(background,(0,0)) #绘制背景,把绘制背景放到前面,在暂停是遮挡换面,防作弊 #有剩余生命(life_num不为零) 和 没有暂停执行子循环 if life_num and not paused: #检查用户键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() #绘制全屏炸弹补给并检查是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image,bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply,me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False #绘制超级子弹补给并检查是否获得 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image,bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply,me): get_bullet_sound.play() #发射超级子弹 is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False #-----------------图片绘制-------------------- #每当被10整除 调用一次,相当于没10帧发射一颗子弹 if not(delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset((me.rect.centerx - 33,me.rect.centery)) bullets[bullet2_index+1].reset((me.rect.centerx + 30,me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) #设置子弹位置在飞机顶端中央 bullet1_index = (bullet1_index + 1) % BULLET1_NUM # #检查子弹是否击中飞机 for b in bullets: if b.active: b.move() screen.blit(b.image,b.rect) enemy_hit = pygame.sprite.spritecollide(b,enemies,False,pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit = True #被击中时为True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False #绘制大型飞机 for each in big_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit,each.rect) each.hit = False else: if switch_image: screen.blit(each.image1,each.rect) else: screen.blit(each.image2,each.rect) #绘制血槽 pygame.draw.line(screen,BLACK,\ (each.rect.left,each.rect.top - 5),\ (each.rect.left,each.rect.top - 5),2) #当生命对于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen,energy_color,\ (each.rect.left,each.rect.top - 5),\ (each.rect.left + each.rect.width * energy_remain,\ each.rect.top - 5),2) #即将出现画面时,播放音效 if each.rect.bottom == -50: enemy3_fly_sound.play(-1) #-1循环播放 else: if e3_destroy_index == 0: #播放销毁图片及音效 enemy3_down_sound.play() #active = False 时毁灭飞机; #delay % 3 是 取模余3是进延迟播放 if not(delay % 3): screen.blit(each.destroy_images[e3_destroy_index],each.rect) e3_destroy_index =(e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 #在敌机销毁时加分数 each.reset() #重置位置 #绘制中型飞机 for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit,each.rect) each.hit = False else: screen.blit(each.image,each.rect) #绘制血槽 pygame.draw.line(screen,BLACK,\ (each.rect.left,each.rect.top - 5),\ (each.rect.left,each.rect.top - 5),2) #当生命对于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen,energy_color,\ (each.rect.left,each.rect.top - 5),\ (each.rect.left + each.rect.width * energy_remain,\ each.rect.top - 5),2) else: if e2_destroy_index == 0: #active = False 时毁灭飞机;播放销毁图片及音效 enemy2_down_sound.play() #delay % 3 是 取模余3是进延迟播放 if not(delay % 3): screen.blit(each.destroy_images[e2_destroy_index],each.rect) e2_destroy_index =(e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 #在敌机销毁时加分数 each.reset() #重置位置 #绘制小型飞机 for each in small_enemies: if each.active: each.move() screen.blit(each.image,each.rect) else: if e1_destroy_index == 0: #active = False 时毁灭飞机;播放销毁图片及音效 enemy1_down_sound.play() #delay % 3 是 取模余3是进延迟播放 if not(delay % 3): screen.blit(each.destroy_images[e1_destroy_index],each.rect) e1_destroy_index =(e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 #在敌机销毁时加分数 each.reset() #重置位置 #检测我方飞机是否被撞 enemies_down = pygame.sprite.spritecollide(me,enemies,False,pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False #绘制我方飞机 if me.active: if switch_image: screen.blit(me.image1,me.rect) else: screen.blit(me.image2,me.rect) else: #active = False 时毁灭飞机;播放销毁图片及音效 me_down_sound.play() #delay % 3 是 取模余3是进延迟播放 if not(delay % 3): screen.blit(me.destroy_images[me_destroy_index],me.rect) me_destroy_index =(me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num-= 1 me.reset() #重置位置 pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) #绘制炸弹数量 bomb_text = bomb_font.render("x %d"% bomb_num,True,WHITE) text_rect = bomb_image.get_rect() screen.blit(bomb_image,(10,height - 10 - bomb_rect.height)) screen.blit(bomb_text,(20 + bomb_rect.width,height - 5 - text_rect.height)) #绘制飞机生命剩余数量 if life_num: for i in range(life_num): screen.blit(life_image,(width - 10 -(i + 1)*life_rect.width,\ height - 10 -life_rect.height)) #绘制分数界面 score_text = score_font.render("Score: %s " %str(score),True,WHITE) screen.blit(score_text,(10,5)) #绘制游戏结束画面 elif life_num == 0: #停止背景音乐 pygame.mixer.music.stop() #停止音效 pygame.mixer.stop() #停止发放补给 pygame.time.set_timer(SUPPLY_TIME,0) #隐藏暂停按钮 BUTTON_ON = False if not recorded: recorded = True #读取历史最高得分 with open("record.txt","r") as f: record_score = int(f.read()) if score > record_score: with open("record.txt","w") as f: f.write(str(score)) #绘制结束画面 record_score_text = score_font.render("Best:%s"%record_score,True,WHITE) screen.blit(record_score_text,(50,50)) gameover_text1 = gameover_font.render("Your Score",True,WHITE) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left,gameover_text1_rect.top = (width - gameover_text1_rect.width) //2, height//3 screen.blit(gameover_text1,gameover_text1_rect) gameover_text2 = gameover_font.render(str(score),True,WHITE) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left,gameover_text2_rect.top = (width - gameover_text2_rect.width) // 2,\ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2,gameover_text2_rect) again_rect.left,again_rect.top = (width - again_rect.width) // 2,\ gameover_text2_rect.bottom + 50 screen.blit(again_image,again_rect) gameover_rect.left,gameover_rect.top = (width - gameover_rect.width) // 2,\ again_rect.bottom + 10 screen.blit(gameover_image,gameover_rect) #检测用户的鼠标操作 #如果用户按下鼠标左键 if pygame.mouse.get_pressed()[0]: #获取鼠标坐标 pos = pygame.mouse.get_pos() #如果用户点击“重新开始” if again_rect.left < pos[0] < again_rect.right and again_rect.top < pos[1] <again_rect.bottom: main() #如果用户点击“结束游戏” elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: pygame.quit() sys.exit() #绘制暂停按钮 if BUTTON_ON: screen.blit(paused_image,paused_rect) if not(delay % 5): switch_image = not switch_image #在循环里不断切换状态 #延时器 delay -= 1 if not delay: delay = 100 pygame.display.flip() #刷新画面 clock.tick(60) #每秒60帧
def main(): pygame.mixer.music.play(-1) #生成影魔 me = shadowfriend.ShadowFriend(bg_size) #生成敌方精灵组 enemies = pygame.sprite.Group() #生成斧王 axe = pygame.sprite.Group() add_axe(axe, enemies, 15) #生成潮汐使者 tide = pygame.sprite.Group() add_tide(tide, enemies, 5) #生成肉山大魔王 roshan = pygame.sprite.Group() add_roshan(roshan, enemies, 2) #生成普通子弹 bullet1 = [] bullet1_index = 0 bullet1_num = 4 for i in range(bullet1_num): bullet1.append(bullet.Bullet1(me.rect.midtop)) # 生成超级子弹 bullet2 = [] bullet2_index = 0 bullet2_num = 8 for i in range(bullet2_num//2): bullet2.append(bullet.Bullet2((me.rect.centerx-33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx+30, me.rect.centery))) clock = pygame.time.Clock() #中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 # 统计得分 score = 0 score_font = pygame.font.Font("font/font.ttf", 36) #标志是否暂停游戏 paused = False pause_nor_image = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load("images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load("images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load("images/resume_pressed.png").convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image # 设置难度级别 level = 1 # 用于切换图片 switch_image = True # 全屏炸弹 bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 # 每30秒发放一个补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) king_supply = supply.King_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) # 超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 # 标志是否使用超级子弹 is_double_bullet = False # 解除我方无敌状态定时器 INVINCIBLE_TIME = USEREVENT + 2 # 生命数量 life_image = pygame.image.load("images/life.png").convert_alpha() life_rect = life_image.get_rect() life_num = 3 # 用于阻止重复打开记录文件 recorded = False # 游戏结束画面 gameover_font = pygame.font.Font("font/font.TTF", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() # 用于切换图片 switch_image = True # 用于延迟 delay = 100 running = True while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = resume_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() Choice = choice([0, 1, 2]) if Choice == 0: bomb_supply.reset() elif Choice == 1: king_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False is_king = False pygame.time.set_timer(INVINCIBLE_TIME, 0) # 根据用户的得分增加难度 if level == 1 and score > 50000: level = 2 upgrade_sound.play() # 增加3个斧王、2个潮汐和1个肉山 add_axe(axe, enemies, 3) add_tide(tide, enemies, 2) add_roshan(roshan, enemies, 1) # 提升斧王的速度 inc_speed(axe, 1) elif level == 2 and score > 300000: level = 3 upgrade_sound.play() # 增加5个斧王、3个潮汐和2个肉山 add_axe(axe, enemies, 5) add_tide(tide, enemies, 3) add_roshan(roshan, enemies, 2) # 提升斧王的速度 inc_speed(axe, 1) inc_speed(tide, 1) elif level == 3 and score > 600000: level = 4 upgrade_sound.play() # 增加5个斧王、3个潮汐和2个肉山 add_axe(axe, enemies, 5) add_tide(tide, enemies, 3) add_roshan(roshan, enemies, 2) # 提升斧王、潮汐的速度 inc_speed(axe, 1) inc_speed(tide, 1) elif level == 4 and score > 1000000: level = 5 upgrade_sound.play() # 增加5个斧王、3个潮汐和2个肉山 add_axe(axe, enemies, 5) add_tide(tide, enemies, 3) add_roshan(roshan, enemies, 2) # 提升斧王、潮汐的速度 inc_speed(axe, 1) inc_speed(tide, 1) screen.blit(background, (0, 0)) # 在仍有生命并且未暂停的情况下 if life_num and not paused: # 检测用户的键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() # 绘制魂之挽歌补给并检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False # 绘制超级子弹补给并检测是否获得 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False # 绘制黑黄杖补给并检测是否获得 if king_supply.active: king_supply.move() screen.blit(king_supply.image, king_supply.rect) if pygame.sprite.collide_mask(king_supply, me): get_king_sound.play() me.invincible = True pygame.time.set_timer(INVINCIBLE_TIME, 8 * 1000) king_supply.active = False # 发射子弹 if not (delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset((me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset((me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % bullet2_num else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % bullet1_num # 绘制子弹是否击中敌人 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide(b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in tide or e in roshan: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False # 绘制roshan for each in roshan: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # 当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.Roshan.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) # roshan时出现时,播放音效(大魔王登场啦!!!) if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: # 毁灭 if not (delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 5 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 each.reset() # 绘制tide for each in tide: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # 当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.Tide.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) else: # 毁灭 if not (delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 each.reset() # 绘制axe for each in axe: if each.active: each.move() screen.blit(each.image, each.rect) else: # 毁灭 if not (delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() # 检测我放飞机是否碰撞 enemies_down = pygame.sprite.spritecollide(me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False # 绘制影魔 if me.active: if me.invincible == True: screen.blit(me.invincible_image, me.rect) else: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 1 * 1000) # 绘制魂之挽歌数量 bomb_text = bomb_font.render("x %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # 绘制剩余生命数量 if life_num: for i in range(life_num): screen.blit(life_image, \ (width - 10 - (i + 1) * life_rect.width, \ height - 10 - life_rect.height)) # 绘制得分 score_text = score_font.render("Score : %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) # 绘制游戏结束画面 elif life_num == 0: # 背景音乐停止 pygame.mixer.music.stop() # 停止全部音效 pygame.mixer.stop() # 停止发放补给 pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True # 读取历史最高得分 with open('record.txt', 'r') as f: record_score = int(f.read()) # 如果玩家得分高于历史最高得分,则存档 if score > record_score: with open('record.txt', 'w') as f: f.write(str(score)) # 绘制结束画面 record_score_text = score_font.render("Best : %d" % record_score, True, WHITE) screen.blit(record_score_text, (50, 50)) gameover_text1 = gameover_font.render("Your Score", True, WHITE) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = \ (width - again_rect.width) // 2, \ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) # 检测玩家的鼠标操作 # 如果玩家按下鼠标左键 if pygame.mouse.get_pressed()[0]: # 获取鼠标坐标 pos = pygame.mouse.get_pos() # 如果玩家点击重新开始 if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: # 调用main(),重新开始游戏 main() # 如果玩家点击结束游戏 elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: # 退出游戏 pygame.quit() sys.exit() # 切换图片 if not (delay % 10): switch_image = not switch_image delay -= 1 if not delay: delay = 100 # 显示 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) # 生成我方飞机 me = myplane.MyPlane(bg_size) enemies = pygame.sprite.Group() # 生成敌方小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) # 生成敌方中型飞机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) # 生成敌方大型飞机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) # 生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # 生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) clock = pygame.time.Clock() # 中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 # 统计得分 score = 0 score_font = pygame.font.Font("font/font.ttf", 36) # 标志是否暂停游戏 paused = False pause_nor_image = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load( "images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load( "images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load( "images/resume_pressed.png").convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image # 设置难度级别 level = 1 # 全屏炸弹 bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 # 每30秒发放一个补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) # 超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 # 标志是否使用超级子弹 is_double_bullet = False # 用于切换图片 switch_image = True # 用于延迟 delay = 100 running = True while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) # 根据用户的得分增加难度 if level == 1 and score > 50000: level = 2 upgrade_sound.play() # 增加3架小型敌机、2架中型敌机和1架大型敌机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) # 提升小型敌机的速度 inc_speed(small_enemies, 1) elif level == 2 and score > 300000: level = 3 upgrade_sound.play() # 增加5架小型敌机、3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升小型敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 3 and score > 600000: level = 4 upgrade_sound.play() # 增加5架小型敌机、3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升小型敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 4 and score > 1000000: level = 5 upgrade_sound.play() # 增加5架小型敌机、3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升小型敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) screen.blit(background, (0, 0)) if not paused: # 检测用户的键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() # 绘制全屏炸弹补给并检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False # 绘制超级子弹补给并检测是否获得 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False # 发射子弹 if not (delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM # 检测子弹是否击中敌机 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False # 绘制大型敌机 for each in big_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # 当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) # 即将出现在画面中,播放音效 if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: # 毁灭 if not (delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 each.reset() # 绘制中型敌机: for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # 当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) else: # 毁灭 if not (delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 each.reset() # 绘制小型敌机: for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: # 毁灭 if not (delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() # 检测我方飞机是否被撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down: # me.active = False for e in enemies_down: e.active = False # 绘制我方飞机 if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: # 毁灭 if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: print("Game Over!") running = False # 绘制全屏炸弹数量 bomb_text = bomb_font.render("× %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # 绘制得分 score_text = score_font.render("Score : %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) # 绘制暂停按钮 screen.blit(paused_image, paused_rect) # 切换图片 if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) clock = pygame.time.Clock() running = True # 用于飞机图片切换 switch_fly = True # 图片切换延迟 delay = 100 # 中弹图片索引 e1_destory_index = 0 e2_destory_index = 0 e3_destory_index = 0 me_destory_index = 0 # 统计得分 score = 0 # 暂停相关 paused = False pause_nor_image = pygame.image.load( 'image/game_pause_nor.png').convert_alpha() pause_pressed_image = pygame.image.load( 'image/game_pause_pressed.png').convert_alpha() resume_nor_image = pygame.image.load( 'image/game_resume_nor.png').convert_alpha() resume_pressed_image = pygame.image.load( 'image/game_resume_pressed.png').convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image # 游戏结束画面 game_over_font = pygame.font.Font('font/Marker Felt.ttf', 48) again_image1 = pygame.image.load('image/restart_nor.png').convert_alpha() again_image2 = pygame.image.load('image/restart_sel.png').convert_alpha() again_image = again_image1 again_rect = again_image.get_rect() gameover_image1 = pygame.image.load('image/quit_nor.png').convert_alpha() gameover_image2 = pygame.image.load('image/quit_sel.png').convert_alpha() gameover_image = gameover_image1 gameover_rect = gameover_image.get_rect() # 设置游戏难度 level = 1 # 全屏炸弹 bomb_image = pygame.image.load('image/bomb.png').convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font('font/Marker Felt.ttf', 48) bomb_num = 3 # 每30秒触发一个补给包 bullet_supply = supply.Bullet_Supply(size) bomb_supply = supply.Bomb_Supply(size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) # 超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 # 无敌状态定时器 INVINCIBLE_TIME = USEREVENT + 2 # 设置子弹标志 is_double_bullet = False # 生命数量 life_image = pygame.image.load('image/plane.png').convert_alpha() life_rect = life_image.get_rect() life_num = 3 # 限制打开文件次数 recorded = False # 生成我方飞机 me = myplane.MyPlane(size) # 生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # 生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 16 for i in range(BULLET2_NUM): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 33, me.rect.centery))) #敌方飞机 enemies = pygame.sprite.Group() # 生成敌方小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) # 生成敌方中型飞机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) # 生成敌方大型飞机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused_image == pause_pressed_image: paused_image = resume_pressed_image else: paused_image = pause_pressed_image if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: # supply_sound.play() if choice([True, False]): bullet_supply.reset() else: bomb_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) # 根据得分增加难度 if level == 1 and score > 50000: level = 2 upgrade_sound.play() # 增加3架小,2架中,1架大 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) # 提升飞机速度 inc_speed(small_enemies, 1) elif level == 2 and score > 300000: level = 3 upgrade_sound.play() # 增加5架小,3架中,2架大 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升飞机速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 3 and score > 600000: level = 4 upgrade_sound.play() # 增加5架小,3架中,2架大 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升飞机速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 4 and score > 1000000: level = 5 upgrade_sound.play() # 增加5架小,3架中,2架大 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升飞机速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) screen.blit(background, (0, 0)) # 检测用户键盘操作 keys = pygame.key.get_pressed() if keys[K_ESCAPE]: pygame.quit() sys.exit() if life_num: if not paused: if keys[K_w] or keys[K_UP]: me.moveUp() if keys[K_s] or keys[K_DOWN]: me.moveDown() if keys[K_a] or keys[K_LEFT]: me.moveLeft() if keys[K_d] or keys[K_RIGHT]: me.moveRight() # 绘制补给并检测 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False # 发射子弹 if not (delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 33, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM # 检测子弹是否击中 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.energy -= 1 e.hit = True if e.energy == 0: e.active = False else: e.active = False # 绘制大型敌机 for each in big_enemies: if each.active: each.move() if each.hit: #绘制被击中特效 screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_fly: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) #当生命大于20%时显示绿色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line( screen, energy_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) #即将出现时播放音效 if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: #毁灭 if not (delay % 3): if e3_destory_index == 0: enemy3_down_sound.play() screen.blit(each.destory_images[e3_destory_index], each.rect) e3_destory_index = (e3_destory_index + 1) % 6 if e3_destory_index == 0: score += 10000 enemy3_fly_sound.stop() each.reset() # 绘制中型敌机 for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) #当生命大于20%时显示绿色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line( screen, energy_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) else: #毁灭 if not (delay % 3): if e2_destory_index == 0: enemy2_down_sound.play() screen.blit(each.destory_images[e2_destory_index], each.rect) e2_destory_index = (e2_destory_index + 1) % 4 if e2_destory_index == 0: score += 6000 each.reset() # 绘制小型敌机 for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: #毁灭 if not (delay % 3): if e1_destory_index == 0: enemy1_down_sound.play() screen.blit(each.destory_images[e1_destory_index], each.rect) e1_destory_index = (e1_destory_index + 1) % 4 if e1_destory_index == 0: score += 1000 each.reset() # 检测我方飞机是否被撞(精确) enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False # 绘制我方飞机 if not (delay % 5): switch_fly = not switch_fly if me.active: if switch_fly: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: #我方飞机毁灭 if not (delay % 3): if me_destory_index == 0: me_down_sound.play() screen.blit(me.destory_images[me_destory_index], me.rect) me_destory_index = (me_destory_index + 1) % 4 if me_destory_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) # 绘制炸弹 bomb_text = bomb_font.render("x " + str(bomb_num), True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit( bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # 绘制生命数量 if life_num: for i in range(life_num): screen.blit(life_image, (width - 10 - (i + 1) * life_rect.width, height - 10 - life_rect.height)) #绘制暂停按钮 screen.blit(paused_image, paused_rect) score_text = score_font.render("Score: " + str(score), True, WHITE) screen.blit(score_text, (10, 5)) else: # bgm停止 pygame.mixer.music.stop() pygame.mixer.stop() # 计时器停止 pygame.time.set_timer(SUPPLY_TIME, 0) # 读取历史记录 if not recorded: recorded = True with open('record.txt', 'r') as f: record_score = int(f.read()) # 对比分数 if score > record_score: with open('record.txt', 'w') as f: f.write(str(score)) # 绘制结束画面 record_score_text = game_over_font.render( "Best: " + str(record_score), True, BLACK) screen.blit(record_score_text, (50, 50)) gameover_text = game_over_font.render("Your Score: " + str(score), True, BLACK) gameover_text_rect = gameover_text.get_rect() gameover_text_rect.left, gameover_text_rect.top = ( width - gameover_text_rect.width ) // 2, height // 2 - gameover_text_rect.height - 10 screen.blit(gameover_text, gameover_text_rect) again_rect.left, again_rect.top = ( width - again_rect.width) // 2, gameover_text_rect.bottom + 10 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = ( width - gameover_rect.width) // 2, again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) #检测用户操作 if pygame.mouse.get_pressed()[0]: pos = pygame.mouse.get_pos() if again_rect.left < pos[ 0] < again_rect.right and again_rect.top < pos[ 1] < again_rect.bottom: main() elif gameover_rect.left < pos[ 0] < gameover_rect.right and gameover_rect.top < pos[ 1] < gameover_rect.bottom: pygame.quit() sys.exit() else: pos = pygame.mouse.get_pos() if again_rect.left < pos[ 0] < again_rect.right and again_rect.top < pos[ 1] < again_rect.bottom: again_image = again_image2 else: again_image = again_image1 if gameover_rect.left < pos[ 0] < gameover_rect.right and gameover_rect.top < pos[ 1] < gameover_rect.bottom: gameover_image = gameover_image2 else: gameover_image = gameover_image1 delay -= 1 if not delay: delay = 100 pygame.display.update() clock.tick(60)
def main(): pygame.mixer.music.play(-1) #生成我方飞机 me = myplane.Myplane(bg_size) #切换我方飞机图片 switch_image = True #生成敌方飞机 enemies = pygame.sprite.Group() small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) #生成普通子弹 bullet1 = [] bullet1_index = 0 BULLEFT1_NUM = 4 for i in range(BULLEFT1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) #生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append( bullet.Bullet2((me.rect.centerx - 33, me.rect.centery - 30))) bullet2.append( bullet.Bullet2((me.rect.centerx + 33, me.rect.centery - 30))) #中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 #统计分数 score = 0 score_front = pygame.font.Font('font/font.ttf', 36) #标志是否暂停游戏 paused = False pause_nor_image = pygame.image.load('images/pause_nor.png').convert_alpha() pause_pressed_image = pygame.image.load( 'images/pause_pressed.png').convert_alpha() resume_nor_image = pygame.image.load( 'images/resume_nor.png').convert_alpha() resume_pressed_image = pygame.image.load( 'images/resume_pressed.png').convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image #游戏结束画面 again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() #设置难度级别 level = 1 #全屏炸弹 bomb_image = pygame.image.load('images/bomb.png').convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font('font/font.ttf', 40) bomb_num = 3 # 每30秒发放补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 100) #超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 #标记超级子弹 is_double_bullet = False #解除无敌计时器 INVINCIBLE_TIME = USEREVENT + 2 #飞机生命 life_image = pygame.image.load('images/life.png').convert_alpha() life_rect = life_image.get_rect() life_num = 3 #用于延迟 delay = 100 clock = pygame.time.Clock() running = True recorded = False while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) #根据得分增加难度 if level == 1 and score > 50000: level = 2 upgrade_sound.play() #增加敌机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) #提升敌机速度 inc_speed(small_enemies, 1) elif level == 2 and score > 300000: level = 3 upgrade_sound.play() #增加敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升敌机速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 3 and score > 600000: level = 4 upgrade_sound.play() #增加敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升敌机速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 4 and score > 100000: level = 5 upgrade_sound.play() #增加敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升敌机速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) screen.blit(background, (0, 0)) if life_num and not paused: #检测键盘操作 key_preesd = pygame.key.get_pressed() if key_preesd[K_w] or key_preesd[K_UP]: me.moveUp() if key_preesd[K_s] or key_preesd[K_DOWN]: me.moveDown() if key_preesd[K_a] or key_preesd[K_LEFT]: me.moveLeft() if key_preesd[K_d] or key_preesd[K_RIGHT]: me.moveRight() #绘制补给并检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False #h绘制超级子弹并检测是否获得 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() #发射超级子弹 is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False #发射子弹 if not (delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 33, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLEFT1_NUM #检测子弹碰撞 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False #绘制大型飞机 for each in big_enemies: if each.active: each.move() if each.hit: #绘制被攻击图片 screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) #绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5),\ (each.rect.right, each.rect.top -5),\ 2) #当生命大于20%显示绿色,否则 红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top -5 ), \ 2) #即将出现画面中,播放音效 if each.rect.bottom == -50: enemy3_fly_sound.play() else: #毁灭 if not (delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 each.reset() #绘制中型机 for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) e.hit = False else: screen.blit(each.image, each.rect) #绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5),\ (each.rect.right, each.rect.top -5),\ 2) #当生命大于20%显示绿色,否则 红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top -5 ), \ 2) else: #毁灭 if not (delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 each.reset() #绘制小型机 for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: #毁灭 if not (delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() #检测我放飞机碰撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False #绘制我方飞机 if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: #毁灭 if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) #绘制剩余炸弹 bomb_text = bomb_font.render('x %d ' % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # 绘制得分 score_text = score_front.render('Score : %s ' % str(score), True, WHITE) screen.blit(score_text, (10, 5)) # 绘制飞机生命数量 if life_num: for i in range(life_num): screen.blit(life_image, (width - 10 - (i + 1) * life_rect.width, height - 10 - life_rect.height)) elif life_num == 0: #游戏结束 pygame.mixer.music.stop() pygame.mixer.stop() pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True #读取历史最高分 with open('record.txt', 'r') as f: record_score = int(f.read()) #存档分数 if score > record_score: with open('record.txt', 'w') as f: f.write(str(score)) #绘制结束界面 record_score_text = score_front.render( 'Best : %s ' % str(record_score), True, WHITE) screen.blit(record_score_text, (50, 50)) gameover_text = score_front.render('Your Score: %s ' % str(score), True, WHITE) gameover_text_rect = gameover_text.get_rect() gameover_text_rect.left, gameover_text_rect.top = ( width - gameover_text_rect.width) // 2, height // 2 screen.blit(gameover_text, (gameover_text_rect.left, gameover_text_rect.top)) again_rect.left, again_rect.top = ( width - again_rect.width) // 2, gameover_text_rect.bottom + 50 screen.blit(again_image, (again_rect.left, again_rect.top)) gameover_rect.left, gameover_rect.top = ( width - gameover_rect.width) // 2, again_rect.bottom + 10 screen.blit(gameover_image, (gameover_rect.left, gameover_rect.top)) #检测用户点击操作 if pygame.mouse.get_pressed()[0]: pos = pygame.mouse.get_pos() if again_rect.left < pos[ 0] < again_rect.right and again_rect.top < pos[ 1] < again_rect.bottom: main() elif gameover_rect.left < pos[ 0] < gameover_rect.right and gameover_rect.top < pos[ 1] < gameover_rect.bottom: pygame.quit() sys.exit() #绘制暂停按钮 screen.blit(paused_image, paused_rect) #切换图片 if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): clock = pygame.time.Clock() pygame.mixer.music.play(-1) flyWight = flywight.Common_FlyWight() #生成飞机 me = plane_factory.ClientPlaneFactory.createPlane(bg_size)#生成我方飞机 enemy_plane = pygame.sprite.Group()#敌方飞机集合 #获取用户设置的关卡等级,以此用于敌军集合的生成,且生成敌军 readyForGame(clock, flyWight, enemy_plane) #生成子弹 bulletGroup = bullet.BulletGroup(me) #给飞机装配子弹 me.fire_command = command.FireBulletCommand(bulletGroup) #生成补给 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) supplyFlyWight = flywight.Supply_FlyWight() pygame.time.set_timer(supplyFlyWight.SUPPLY_TIME, 30 * 1000) #生成障碍物 aerolite_barrier = barrier.Aerolite_Barrier(bg_size) barrierFlyWight = flywight.Aerolite_Barrier_FlyWight() pygame.time.set_timer(barrierFlyWight.BARRIER_TIME, 10 * 1000) score = 0#统计得分 delay = 100#延迟 while me.life_num: #TODO:对事件进行分析 for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == KEYDOWN:#键盘事件 if event.key == K_SPACE:#空格键 使用炸弹 if me.bomb_num:#使用炸弹 me.bomb_num -= 1 supplyFlyWight.bomb_sound.play() if aerolite_barrier.rect.bottom > 0: aerolite_barrier.active = False#在界面中的障碍物 for each in enemy_plane: if each.rect.bottom > 0:#在界面中的敌机 each.active = False elif event.type == supplyFlyWight.SUPPLY_TIME:#补给时间 supplyFlyWight.supply_sound.play() #随机生成补给 if random.choice([True, False]): bullet_supply.reset() else: bomb_supply.reset() elif event.type == supplyFlyWight.DOUBLE_BULLET_TIME: me.is_double_bullet = False pygame.time.set_timer(supplyFlyWight.DOUBLE_BULLET_TIME, 0) elif event.type == barrierFlyWight.BARRIER_TIME: aerolite_barrier.reset() screen.blit(flyWight.background, (0, 0)) #检测键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() #绘制补给 bullet_supply.drawSupply(screen, me) bomb_supply.drawSupply(screen, me) #绘制障碍物 aerolite_barrier.drawBarrier(screen, me) #发射子弹 if not (delay % 10): me.fireBullet() #检测子弹是否击中物体 bulletGroup.hitPlaneAndBarrier(screen, enemy_plane, aerolite_barrier) #绘制敌机 for each in enemy_plane: getScore = each.drawPlane(screen, delay) if getScore != 0: score += getScore each.reset() #检测客户机是否被撞 me.checkPlane(enemy_plane) #绘制客户机 getScore = me.drawPlane(screen, delay) score += getScore #画出生命值和分数 me.drawLifeNumAndScore(screen, flyWight.score_font, score) delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60) gameOver(clock, flyWight, score)
def main(): run = True # 循环控制参数 start = False # 游戏开始参数 paussed = True # 暂停标志参数 clock = pygame.time.Clock() # 帧率控制 delay = 100 # 延迟设置 score = 0 # 设置得分 grade1 = 50 # 小型敌机分数 grade2 = 300 # 中型敌机分数 grade3 = 600 # 大型敌机分数 level = 1 # 等级水平 life_num = 3 # 生命数 # 字体设置 score_font = pygame.font.Font("font/font.ttf", 35) game_over_font = pygame.font.Font("font/font.ttf", 30) # 设置"游戏准备"图片精灵 game_loadings = list() game_loadings_index = 0 game_loadings_num = 3 game_loadings.append(game_loading1) game_loadings.append(game_loading2) game_loadings.append(game_loading3) # 背景音乐播放 bg_music.play(-1) # 实例化我方飞机 hero = plane.Plane(bg_size) # 实例化敌机组 enemies = pygame.sprite.Group() # 实例化小型敌机 mini_enemise = pygame.sprite.Group() add_enemies('mini', bg_size, mini_enemise, enemies, 16) # 实例化中型敌机 medium_enemise = pygame.sprite.Group() add_enemies('medium', bg_size, medium_enemise, enemies, 8) # 实例化大型敌机 large_enemise = pygame.sprite.Group() add_enemies('large', bg_size, large_enemise, enemies, 4) # 实例化子弹 bullets = [] # 子弹索引下标 bullets_index = 0 # 子弹数目 bullet_num = 4 # 炮弹数目 bomb_num = 3 for i in range(bullet_num): bullets.append(bullet.Bullet(hero.rect.midtop)) # 实例化补给 bomb_supply = supply.Bomb_Supply(bg_size) # 设置一个定时事件 supply_time = USEREVENT pygame.time.set_timer(supply_time, msec) # 游戏循环 while run: # 事件检测 for event in pygame.event.get(): # 右上角关闭按钮检测 if event.type == QUIT: pygame.quit() sys.exit() # 鼠标点击检测 elif event.type == MOUSEBUTTONDOWN: if event.button == 1: # 游戏开始 start = True if event.button == 1 and paused_rect.collidepoint(event.pos): paussed = not paussed if not paussed: pygame.time.set_timer(supply_time, 0) # 暂停音效 pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(supply_time, msec) # 恢复音效 pygame.mixer.music.unpause() pygame.mixer.unpause() if event.button == 1 and game_restart_rect.collidepoint( event.pos): # 重新开始 main() # 鼠标放置坐标检测 elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paussed: paused_image = game_resume_pressed else: paused_image = game_pause_pressed else: if paussed: paused_image = game_resume_nor else: paused_image = game_pause_nor # 键盘按键检测 elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 enemy3_down_sound.play() # 按下空格后,销毁屏幕内所有敌机 for each in enemies: if each.rect.bottom > 0: each.survival = False # 定时时间检测 elif event.type == supply_time: bomb_supply.set_position() # 视情况提升等级 if level < get_level(score) + 1: level += 1 game_achievement_sound.play() # 增加一定批次的敌机 add_enemies('mini', bg_size, mini_enemise, enemies, 3) add_enemies('medium', bg_size, medium_enemise, enemies, 2) add_enemies('large', bg_size, large_enemise, enemies, 1) # 提升小型敌机速度 up_speed(mini_enemise, 1) print('等级提升') if not (level % 2) and bullet_num < 6: # 每提升两次敌机数量,就加一发子弹,上限是6 print('子弹数目增加') bullet_num += 1 bullets.append(bullet.Bullet(hero.rect.midtop)) # 游戏开始 if start: # 绘制背景图像 screen.blit(background, (0, 0)) # 绘制分数 score_text = score_font.render("Score : %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) # 绘制炸弹 bomb_text = bomb_font.render("× %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # 绘制暂停按钮 screen.blit(paused_image, paused_rect) if life_num and paussed: # 碰撞检测 enemies_down = pygame.sprite.spritecollide( hero, enemies, False, pygame.sprite.collide_mask) if enemies_down: hero.survival = False for enemy_down in enemies_down: enemy_down.survival = False # 发射子弹 if not (delay % bullet_speed): bullets[bullets_index].set_position(hero.rect.midtop) bullets_index = (bullets_index + 1) % bullet_num # 子弹碰撞检测 for b in bullets: if b.survival: b.move() screen.blit(b.bullet, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) # 被击中后 if enemy_hit: b.survival = False for e in enemy_hit: if e in medium_enemise or e in large_enemise: e.hp -= 1 e.hit = True if e.hp == 0: e.survival = False else: e.survival = False # 绘制炸弹补给 if bomb_supply.survival: bomb_supply.move() screen.blit(bomb_supply.bomb, bomb_supply.rect) # 炸弹补给碰撞检测 if pygame.sprite.collide_mask(bomb_supply, hero): if bomb_num < 3: bomb_num += 1 # 销毁炸弹补给 bomb_supply.survival = False # 绘制小型敌机图像 for mini_enemy in mini_enemise: # 存活判断 if mini_enemy.survival: # 小型敌机移动 mini_enemy.move() # 绘制图像 screen.blit(mini_enemy.enemy, mini_enemy.rect) else: # 销毁敌机 if not (delay % destroy_speed): if mini_enemy.spirits_index == 0: # 播放敌机销毁声音 enemy1_down_sound.play() # 绘制销毁动画 screen.blit( mini_enemy.death_spirits[ mini_enemy.spirits_index], mini_enemy.rect) mini_enemy.spirits_index = mini_enemy.spirits_index + 1 if mini_enemy.spirits_index == 4: # 增加分数 score += grade1 # 重新设置敌机 mini_enemy.set_position() # 绘制中型敌机图像 for medium_enemy in medium_enemise: # 存活判断 if medium_enemy.survival: # 中型敌机移动 medium_enemy.move() # 被击中判定 if medium_enemy.hit: screen.blit(medium_enemy.enemy_hit, medium_enemy.rect) medium_enemy.hit = False else: # 绘制图像 screen.blit(medium_enemy.enemy, medium_enemy.rect) # 绘制血槽 draw_start = (medium_enemy.rect.left, medium_enemy.rect.top - 5) draw_end = (medium_enemy.rect.right, medium_enemy.rect.top - 5) pygame.draw.line(screen, RED, draw_start, draw_end, 2) # 计算剩余血量 surplus_hp = medium_enemy.hp / enemy.MediumEnemy.hp draw_end = (medium_enemy.rect.left + medium_enemy.rect.width * surplus_hp, medium_enemy.rect.top - 5) pygame.draw.line(screen, GREEN, draw_start, draw_end, 2) else: # 销毁敌机 if not (delay % destroy_speed): if medium_enemy.spirits_index == 0: # 播放敌机销毁声音 enemy2_down_sound.play() # 绘制销毁动画 screen.blit( medium_enemy.death_spirits[ medium_enemy.spirits_index], medium_enemy.rect) medium_enemy.spirits_index = medium_enemy.spirits_index + 1 if medium_enemy.spirits_index == 4: # 增加分数 score += grade2 # 重新设置敌机 medium_enemy.set_position() # 绘制大型敌机图像 for large_enemy in large_enemise: # 存活判断 if large_enemy.survival: # 大型敌机移动 large_enemy.move() # 被击中判定 if large_enemy.hit: screen.blit(large_enemy.enemy_hit, large_enemy.rect) large_enemy.hit = False else: # 绘制敌机图形 screen.blit(large_enemy.enemy, large_enemy.rect) # 绘制血槽 draw_start = (large_enemy.rect.left, large_enemy.rect.top - 5) draw_end = (large_enemy.rect.right, large_enemy.rect.top - 5) pygame.draw.line(screen, RED, draw_start, draw_end, 2) # 计算剩余血量 surplus_hp = large_enemy.hp / enemy.LargeEnemy.hp draw_end = (large_enemy.rect.left + large_enemy.rect.width * surplus_hp, large_enemy.rect.top - 5) pygame.draw.line(screen, GREEN, draw_start, draw_end, 2) if large_enemy.rect.bottom > -50: # 播放敌机飞行声音 enemy3_out_sound.play(-1) else: # 销毁敌机 if not (delay % destroy_speed): if large_enemy.spirits_index == 0: # 播放敌机销毁声音 enemy3_down_sound.play() # 绘制销毁动画 screen.blit( large_enemy.death_spirits[ large_enemy.spirits_index], large_enemy.rect) large_enemy.spirits_index = large_enemy.spirits_index + 1 if large_enemy.spirits_index == 6: # 增加分数 score += grade3 # 关闭音效 enemy3_out_sound.stop() # 重新设置敌机 large_enemy.set_position() # 绘制飞机图像 if hero.survival: # 检测键盘,控制我方飞机移动 hero.move() screen.blit(hero.plane, hero.rect) else: enemy2_down_sound.play() if not (delay % destroy_speed): # 绘制销毁动画 screen.blit(hero.death_spirits[hero.spirits_index], hero.rect) hero.spirits_index = hero.spirits_index + 1 if hero.spirits_index == 3: print("Code Over") life_num -= 1 # 重新设置战机 hero.set_position() # 绘制飞机生命数量 if life_num: for i in range(life_num): life_left = width - 10 - (i + 1) * life_rect.width life_top = height - 10 - life_rect.height screen.blit(life_image, (life_left, life_top)) elif life_num == 0: # 读取历史最高分 highest_score = int() # 判断记录文件是否存在,不存在则创建 if not os.path.exists("score.txt"): #os.mknod("score.txt") highest_score = 0 else: # 文件存在着进行读取 with open("score.txt", "r") as f: highest_score = int(f.read()) f.close() # 若打破记录,则重新写入分数 if score > highest_score: with open("score.txt", "w+") as f: f.write(str(score)) f.close() # 绘制游戏结束背景图 screen.blit(game_over, (0, 0)) # 绘制最终得分 if score < highest_score: game_over_text = game_over_font.render( "%s" % str(score), True, WHITE) else: game_over_text = game_over_font.render( "%s" % str(score), True, WHITE) over_text_width = str(score).__len__() + 50 screen.blit(game_over_text, ((width - over_text_width) / 2, height / 2)) # 绘制历史记录 game_over_text = game_over_font.render( "%s" % "Highest Score: " + str(highest_score), True, WHITE) over_text_width = (str(highest_score).__len__() + 15) * 12 screen.blit(game_over_text, ((width - over_text_width) / 2, height / 2 + 60)) # 绘制重新开始按钮 screen.blit(game_restart, game_restart_rect) # 停止背景音乐 pygame.mixer.music.pause() # 停止音效 pygame.mixer.pause() else: # 绘制游戏停止标志图 screen.blit(game_stop, ((width - game_stop_rect.width) / 2, (height - game_stop_rect.height) / 2)) else: # 绘制背景图像 screen.blit(background, (0, 0)) # 绘制游戏名称 screen.blit(game_start, (0, 0)) # 绘制 loading 图像 game_loading_X = (width - game_loading_rect.width) / 2 game_loading_Y = (height - game_loading_rect.height) / 2 + 50 screen.blit(game_loadings[game_loadings_index], (game_loading_X, game_loading_Y)) # loding 下标变更 if not (delay % 8): game_loadings_index = (game_loadings_index + 1) % game_loadings_num # 绘制界面(双缓冲) pygame.display.flip() # 帧率设置 clock.tick(30) delay -= 1 if delay == 0: delay = 10
def main(): #Set start time point start = time.clock() #Play bgmusic pygame.mixer.music.play(-1) #Generate player's plane me = myplane.MyPlane(bg_size) #Put enemy's planes in a group enemies = pygame.sprite.Group() #Generate small enemy in another group small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) #Generate middle enemy in another group mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) #Generate big enemy in another group big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) #Initiate normal bullet bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 #Set position of bullet for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) #Initiate double bullet bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 #Set position of bullet for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) #Initiate clock clock = pygame.time.Clock() #Hit picture check e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 #Set enemy counter num_se = 0 num_me = 0 num_be = 0 #Set supply bag number num_sb = 0 num_db = 0 #Set super bullet used num_super = 0 #Set score, font and size score = 0 score_font = pygame.font.Font("font/font.ttf", 24) #Check game pause or not paused = False pause_nor_image = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load( "images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load( "images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load( "images/resume_pressed.png").convert_alpha() #Put pause button paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image #Set default difficulty level = 1 #Set super bomb font, picture and number bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 #Provide supply bags every 30 sec bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) #Set double bullet timer DOUBLE_BULLET_TIME = USEREVENT + 1 #Set signal of double bullet is_double_bullet = False #Invincible timer INVINCIBLE_TIME = USEREVENT + 2 #Life number life_image = pygame.image.load("images/life.png").convert_alpha() life_rect = life_image.get_rect() life_num = 3 #Set Game Over screen gameover_font = pygame.font.Font("font/font.TTF", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() #Swith picture switch_image = True #Set delay delay = 100 ######################### #Check running status running = True while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() #Press pause elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused #If game paused, pause the music and pully bag if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() #Change pause button style elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image #Check if use super bomb or not elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 num_super += 1 bomb_sound.play() #Destroy all enemies for each in enemies: if each.rect.bottom > 0: each.active = False #Check if the time is supply time or not elif event.type == SUPPLY_TIME: supply_sound.play() #Choice one random if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() #Check if the time is double bullet time or not elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) #Cancel invincible elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) #Modify difficulty depends on score if level == 1 and score > 200: level = 2 upgrade_sound.play() #Add 3 small enemies, 2 middle enemies and 1 big enemies add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) #Modify small enemies' speed inc_speed(small_enemies, 1) elif level == 2 and score > 2000: level = 3 upgrade_sound.play() #Add 5 small enemies, 3 middle enemies and 2 big enemies add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #Modify small enemies' speed inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 3 and score > 4000: level = 4 upgrade_sound.play() #Add 5 small enemies, 3 middle enemies and 2 big enemies add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #Modify small enemies' speed inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 4 and score > 6000: level = 5 upgrade_sound.play() #Add 5 small enemies, 3 middle enemies and 2 big enemies add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #Modify small enemies' speed inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) #Set screen screen.blit(background, (0, 0)) #render used to change it as surface object score_text = score_font.render("Score : %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) score_text = score_font.render("Small enemy : %s" % str(num_se), True, WHITE) screen.blit(score_text, (10, 30)) score_text = score_font.render("Middle enemy : %s" % str(num_me), True, WHITE) screen.blit(score_text, (10, 55)) score_text = score_font.render("Big enemy : %s" % str(num_be), True, WHITE) screen.blit(score_text, (10, 80)) if life_num and not paused: # Check user's operation key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() #Shoot normal bullet 6/sec if not (delay % 10): bullet_sound.play() #If double bullet, set bullets to double bullets if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) #Load next bullet in bullets[] bullet1_index = (bullet1_index + 1) % BULLET1_NUM #Check if bullets hit enemy or not for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False #One hit decrease one energy for e in enemy_hit: #Middle or big enemy if e in mid_enemies or e in big_enemies: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False #Small enemy else: e.active = False ################################### #Draw supper bullet bag if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) #Check if player catch it or not if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() num_sb += 1 if bomb_num < 3: bomb_num += 1 bomb_supply.active = False #Draw double bullet bag if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) #Check if player catch it or not if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() num_db += 1 is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False #Draw big enemy for each in big_enemies: #Check the enemy alive or destroy if each.active: each.move() #If hit, switch picture if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) #Draw enemy energy pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) #Change the color energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) #Play background music. -1 means continuous if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: #Destroy if not (delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() #Show destroy in progress with 6 pictures screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 100 num_be += 1 each.reset() #Draw middle enemies for each in mid_enemies: #Check the enemy alive or destroy if each.active: each.move() #If hit, switch picture if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) #Draw enemy energy pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) #Change the color energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) else: #Destroy if not (delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() #Show destroy in progress with 4 pictures screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 60 num_me += 1 each.reset() #Draw small enemy for each in small_enemies: #Check the enemy alive or destroy if each.active: each.move() screen.blit(each.image, each.rect) else: #Destroy if not (delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() #Show destroy in progress with 4 pictures screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 10 num_se += 1 each.reset() #Detect collision, check if player's plane touched any enemy plane in group of enemies enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: #If player's plane down, all enemies down. me.active = False for e in enemies_down: e.active = False #Draw player's plane with switching picture if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: #Destroy if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() #Show destroy in progress with 4 pictures screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 #When player's plane down, life count -1 and player will have 3 second without any hurt if me_destroy_index == 0: life_num -= 1 me.reset() #When player's plane down, won't get hurt in 3 sec pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) else: #Set end time point end = time.clock() #Draw super bullet bomb_text = bomb_font.render("× %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) #Draw remain life if life_num: for i in range(life_num): screen.blit(life_image, \ (width-10-(i+1)*life_rect.width, \ height-10-life_rect.height)) ###################### #Set Game Over elif life_num == 0: #Stop background music pygame.mixer.music.stop() #Stop all music pygame.mixer.stop() #Stop provide supply bag pygame.time.set_timer(SUPPLY_TIME, 0) #Draw Game Over Screen #Show the game time total_time = "%d" % (end - start) num_normalbullet = (int)(total_time) * 6 num_doublebullet = num_db * 12 * 18 #Get data from database global download while download == 0: global bestScore, bestNum_se, bestNum_me, bestNum_be, bestTotal_time, bestNum_sb, bestNum_db, bestNum_normalbullet, bestNum_doublebullet, bestNum_super bestScore = mysql.get_bestScore() bestNum_se = mysql.get_bestNum_se() bestNum_me = mysql.get_bestNum_me() bestNum_be = mysql.get_bestNum_be() bestTotal_time = mysql.get_bestTotal_time() bestNum_sb = mysql.get_bestNum_sb() bestNum_db = mysql.get_bestNum_db() bestNum_normalbullet = mysql.get_bestNum_normalbullet() bestNum_doublebullet = mysql.get_bestNum_doublebullet() bestNum_super = mysql.get_bestNum_super() download += 1 #Upload data to database global upload while upload == 0: mysql.upload_score(score,num_se,num_me,num_be,\ total_time,num_sb,num_db,num_normalbullet,\ num_doublebullet,num_super) upload += 1 #Show message in Game Over screen new_record = 0 if int(score) > int(bestScore): score_text = score_font.render("Score : %s" % str(score), True, RED) score_text2 = score_font.render("Best: %s" % str(score), True, WHITE) new_record += 1 screen.blit(score_text, (10, 5)) screen.blit(score_text2, (280, 5)) else: score_text2 = score_font.render("Best: %s" % str(bestScore), True, WHITE) screen.blit(score_text2, (280, 5)) if int(num_se) > bestNum_se: se_text = score_font.render("Small enemy : %s" % str(num_se), True, RED) se_text2 = score_font.render("Best: %s" % str(num_se), True, WHITE) new_record += 1 screen.blit(se_text, (10, 30)) screen.blit(se_text2, (295, 30)) else: se_text2 = score_font.render("Best: %s" % str(bestNum_se), True, WHITE) screen.blit(se_text2, (295, 30)) if int(num_me) > bestNum_me: me_text = score_font.render("Middle enemy : %s" % str(num_me), True, RED) me_text2 = score_font.render("Best: %s" % str(num_me), True, WHITE) new_record += 1 screen.blit(me_text, (10, 55)) screen.blit(me_text2, (320, 55)) else: me_text2 = score_font.render("Best: %s" % str(bestNum_me), True, WHITE) screen.blit(me_text2, (320, 55)) if int(num_be) > bestNum_be: be_text = score_font.render("Big enemy : %s" % str(num_be), True, RED) be_text2 = score_font.render("Best: %s" % str(num_be), True, WHITE) new_record += 1 screen.blit(be_text, (10, 80)) screen.blit(be_text2, (320, 80)) else: be_text2 = score_font.render("Best: %s" % str(bestNum_be), True, WHITE) screen.blit(be_text2, (320, 80)) if int(total_time) > bestTotal_time: Time_text = score_font.render( "Time : %s Seconds" % str(total_time), True, RED) Time_text2 = score_font.render("Best: %s" % str(total_time), True, WHITE) new_record += 1 screen.blit(Time_text, (10, 105)) screen.blit(Time_text2, (320, 105)) else: Time_text = score_font.render( "Time : %s Seconds" % str(total_time), True, WHITE) Time_text2 = score_font.render( "Best: %s" % str(bestTotal_time), True, WHITE) screen.blit(Time_text, (10, 105)) screen.blit(Time_text2, (320, 105)) if int(num_sb) > bestNum_sb: sbb_text = score_font.render( "Super bullet bag accept : %s" % str(num_sb), True, RED) sbb_text2 = score_font.render("Best: %s" % str(num_sb), True, WHITE) new_record += 1 screen.blit(sbb_text, (10, 130)) screen.blit(sbb_text2, (320, 130)) else: sbb_text = score_font.render( "Super bullet bag accept : %s" % str(num_sb), True, WHITE) sbb_text2 = score_font.render("Best: %s" % str(bestNum_sb), True, WHITE) screen.blit(sbb_text, (10, 130)) screen.blit(sbb_text2, (320, 130)) if int(num_db) > bestNum_db: dbb_text = score_font.render( "Double bullet bag accept : %s" % str(num_db), True, RED) dbb_text2 = score_font.render("Best: %s" % str(num_db), True, WHITE) new_record += 1 screen.blit(dbb_text, (10, 155)) screen.blit(dbb_text2, (320, 155)) else: dbb_text = score_font.render( "Double bullet bag accept : %s" % str(num_db), True, WHITE) dbb_text2 = score_font.render("Best: %s" % str(bestNum_db), True, WHITE) screen.blit(dbb_text, (10, 155)) screen.blit(dbb_text2, (320, 155)) if int(num_normalbullet) > bestNum_normalbullet: nb_text = score_font.render( "Normal bullet used : %s" % str(num_normalbullet), True, RED) nb_text2 = score_font.render( "Best: %s" % str(num_normalbullet), True, WHITE) new_record += 1 screen.blit(nb_text, (10, 180)) screen.blit(nb_text2, (320, 180)) else: nb_text = score_font.render( "Normal bullet used : %s" % str(num_normalbullet), True, WHITE) nb_text2 = score_font.render( "Best: %s" % str(bestNum_normalbullet), True, WHITE) screen.blit(nb_text, (10, 180)) screen.blit(nb_text2, (320, 180)) if int(num_doublebullet) > bestNum_doublebullet: db_text = score_font.render( "Double bullet used : %s" % str(num_doublebullet), True, RED) db_text2 = score_font.render( "Best: %s" % str(num_doublebullet), True, WHITE) new_record += 1 screen.blit(db_text, (10, 205)) screen.blit(db_text2, (320, 205)) else: db_text = score_font.render( "Double bullet used : %s" % str(num_doublebullet), True, WHITE) db_text2 = score_font.render( "Best: %s" % str(bestNum_doublebullet), True, WHITE) screen.blit(db_text, (10, 205)) screen.blit(db_text2, (320, 205)) if int(num_super) > bestNum_super: sb_text = score_font.render( "Super bullet used : %s" % str(num_super), True, RED) sb_text2 = score_font.render("Best: %s" % str(num_super), True, WHITE) new_record += 1 screen.blit(sb_text, (10, 230)) screen.blit(sb_text2, (320, 230)) else: sb_text = score_font.render( "Super bullet used : %s" % str(num_super), True, WHITE) sb_text2 = score_font.render("Best: %s" % str(bestNum_super), True, WHITE) screen.blit(sb_text, (10, 230)) screen.blit(sb_text2, (320, 230)) gameover_text1 = gameover_font.render("Game Over", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = 135, 300 screen.blit(gameover_text1, gameover_text1_rect) if new_record > 0: gameover_text2 = gameover_font.render("New Record!!", True, RED) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = 120, 365 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = 90, 465 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = 90, 515 screen.blit(gameover_image, gameover_rect) #Check keyboard #If press left key if pygame.mouse.get_pressed()[0]: #Get position of mouse pos = pygame.mouse.get_pos() #If player press restart if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: #run main again download -= 1 upload -= 1 main() #If press Quit elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: #Game exit pygame.quit() sys.exit() #Draw pause button screen.blit(paused_image, paused_rect) #Switch in every 5 frame if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 #Flip the screen pygame.display.flip() #Set clock clock.tick(60)
def start(): # 播放音乐 pygame.mixer.music.play(-1) # 实例我方飞机 me = myplane.MyPlane(bg_size=bg_size) # 实例敌方飞机 enemies = pygame.sprite.Group() # 实例敌方小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) # 实例敌方中型飞机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) # 实例敌方大型飞机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) # 实例普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # 实例超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) # 中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 # 统计得分 score = 0 score_font = pygame.font.Font("font/rough.ttf", 36) # 标志是否暂停游戏 paused = False paused_nor_image = pygame.image.load( "images/pause_nor.png").convert_alpha() paused_pressed_image = pygame.image.load( "images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load( 'images/resume_nor.png').convert_alpha() resume_pressed_image = pygame.image.load( 'images/resume_pressed.png').convert_alpha() paused_rect = paused_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = paused_nor_image # 设置难度 level = 1 # 全屏炸弹 bomb_image = pygame.image.load('images/bomb.png').convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 # 每30秒发放一个补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) # 超级子弹定时器 DOUBLE_BULLTET_TIME = USEREVENT + 1 # 解除我方重生无敌定时器 INVINCIBLE_TIME = USEREVENT + 2 # 标志是否使用超级子弹 is_double_bullet = False # 生命数量 life_image = pygame.image.load('images/life.png').convert_alpha() life_rect = life_image.get_rect() life_num = 3 # 用于切换我方飞机图片 switch_plane = True # 游戏结束画面 gameover_font = pygame.font.Font("font/font.TTF", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() # 用于延迟切换 delay = 100 # 限制打开一次记录文件 recorded = False clock = pygame.time.Clock() running = True while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = paused_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = paused_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLTET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLTET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) # 根据用户得分增加难度 if level == 1 and score > 5000: level = 2 upgrade_sound.play() # 增加3架小型敌机, 2架中型敌机和1架大型敌机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) # 提升小型敌机的速度 inc_speed(target=small_enemies, inc=1) elif level == 2 and score > 30000: level = 3 upgrade_sound.play() # 增加5架小型敌机, 3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升小型敌机的速度 inc_speed(target=small_enemies, inc=1) inc_speed(target=mid_enemies, inc=1) elif level == 3 and score > 60000: level = 4 upgrade_sound.play() # 增加5架小型敌机, 3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升小型敌机的速度 inc_speed(target=small_enemies, inc=1) inc_speed(target=mid_enemies, inc=1) elif level == 4 and score > 100000: level = 5 upgrade_sound.play() # 增加5架小型敌机, 3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升小型敌机的速度 inc_speed(target=small_enemies, inc=1) inc_speed(target=mid_enemies, inc=1) inc_speed(target=big_enemies, inc=1) screen.blit(background, (0, 0)) if life_num and not paused: # 检测键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() # 绘制全屏炸弹补给 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(me, bomb_supply): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False # 绘制超级子弹补给 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(me, bullet_supply): get_bullet_sound.play() # 发射超级子弹 is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLTET_TIME, 18 * 1000) bullet_supply.active = False # 发射子弹 if not (delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM # 检测子弹是否击中敌机 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for each in enemy_hit: each.hit = True each.energy -= 1 if each.energy == 0: each.active = False # 绘制敌方大型机 for each in big_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_plane: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) # 当生命大于20%显示绿色, 否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line( screen, energy_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) # 即将出现在画面, 播放音效 if each.rect.bottom == -10: enemy3_fly_sound.play(-1) each.appear = True # 离开画面, 关闭音效 if each.rect.bottom < -10 and each.appear: enemy3_fly_sound.stop() each.appear = False else: # 毁灭 if e3_destroy_index == 0: enemy3_down_sound.play() if not (delay % 2): screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 1000 each.reset() # 绘制敌方中型机 for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) # 当生命大于20%显示绿色, 否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line( screen, energy_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) else: # 毁灭 if e2_destroy_index == 0: enemy2_down_sound.play() if not (delay % 2): screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 600 each.reset() # 绘制敌方小型机 for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: # 毁灭 if e1_destroy_index == 0: enemy1_down_sound.play() if not (delay % 2): screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 100 each.reset() # 检测我方飞机碰撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for each in enemies_down: each.active = False # 绘制我方飞机 if me.active: if switch_plane: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: # 毁灭 if me_destroy_index == 0: me_down_sound.play() if not (delay % 2): screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) # 绘制全屏炸弹数量 bomb_text = bomb_font.render("× %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # 绘制剩余生命数量 if life_num: for i in range(life_num): screen.blit(life_image, ((width - 10 - (i + 1) * life_rect.width), height - 10 - life_rect.height)) # 绘制得分 score_text = score_font.render('Score : %d' % score, True, WHITE) screen.blit(score_text, (10, 5)) # 绘制游戏结束画面 elif life_num == 0: # 背景音乐停止 pygame.mixer.music.stop() # 停止全部音效 pygame.mixer.stop() # 停止发放补给 pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True # 读取历史最高分 with open('record.txt', 'r') as f: record_scores = f.readlines() record_score = int(record_scores[0]) for i in range(0, 10): record_scores[i] = record_scores[i].strip("\n") for i in range(0, 10, 1): if score >= int(record_scores[i]): for j in range(9, i - 1, -1): record_scores[j] = record_scores[j - 1] record_scores[i] = score modify(record_scores) break # 绘制结束界面 record_score_text = score_font.render( "Best : %d" % int(record_scores[0]), True, (255, 255, 255)) screen.blit(record_score_text, (50, 50)) gameover_text1 = gameover_font.render("Your Score", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = \ (width - again_rect.width) // 2, \ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) rank_rect.top = gameover_rect.bottom + 10 screen.blit(rank_image, rank_rect) # 检测用户的鼠标操作 # 如果用户按下鼠标左键 if pygame.mouse.get_pressed()[0]: # 获取鼠标坐标 pos = pygame.mouse.get_pos() # 如果用户点击“重新开始” if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: # 调用main函数,重新开始游戏 main() # 如果用户点击“结束游戏” elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: # 退出游戏 pygame.quit() sys.exit() elif rank_rect.left < pos[ 0] < rank_rect.right and rank_rect.top < rank_rect.bottom: rank() # 绘制暂停按钮 screen.blit(paused_image, paused_rect) # 用于切换图片 if not (delay % 11): switch_plane = not switch_plane delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) #生成我方飞机 me = myplane.Myplane(bg_size) #生成敌方飞机 enemies = pygame.sprite.Group() #生成小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) #生成中型飞机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) #生成大型飞机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) #生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1()) #生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM): bullet2.append(bullet.Bullet2()) clock = pygame.time.Clock() #中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 #统计玩家得分 score = 0 score_font = pygame.font.Font('font/font.ttf', 36) #标志是否暂停游戏 paused = False pause_nor_image = pygame.image.load('images/pause_nor.png').convert_alpha() pause_pressed_image = pygame.image.load( 'images/pause_pressed.png').convert_alpha() resume_nor_image = pygame.image.load( 'images/resume_nor.png').convert_alpha() resume_pressed_image = pygame.image.load( 'images/resume_pressed.png').convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image #设置难度级别 level = 1 #全屏炸弹 bomb_image = pygame.image.load('images/bomb.png').convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font('font/font.ttf', 48) bomb_num = 3 #每30秒发放一个补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) #超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 #无敌时间定时器 INVINCIBLE_TIME = USEREVENT + 2 #是否使用超级子弹 is_double_bullet = False #生命数量 life_image = pygame.image.load('images/life.png').convert_alpha() life_rect = life_image.get_rect() life_num = 3 recorded = False # 游戏结束画面 gameover_font = pygame.font.Font("font/font.ttf", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() #用于切换图片 switch_image = True #用于延迟 delay = 100 runing = True while runing: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) #根据用户得分增加难度 if level == 1 and score > 50000: level = 2 upgrade_sound.play() #增加3架小型敌机,2架中型敌机和1架大型敌机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) #提升小型敌机的速度 inc_speed(small_enemies, 1) elif level == 2 and score > 300000: level = 3 upgrade_sound.play() #增加5架小型敌机,3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升小型敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 3 and score > 600000: level = 4 upgrade_sound.play() #增加5架小型敌机,3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升小型敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 4 and score > 1000000: level = 5 upgrade_sound.play() #增加5架小型敌机,3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升小型敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) screen.blit(background, (0, 0)) if life_num and not paused: #检测用户的键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveup() if key_pressed[K_s] or key_pressed[K_DOWN]: me.movedown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveleft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveright() #绘制全屏炸弹补给检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False #绘制超级子弹补给检测是否获得 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False #发射子弹 if not (delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 31, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM #检测子弹是否击中敌机 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.energy -= 1 e.hit = True if e.energy == 0: e.active = False else: e.active = False #绘制大型敌机 for each in big_enemies: if each.active: each.move() if each.hit: #如果被击中中,绘制击中特效 screen.blit(each.image_hit, each.rect) each.hit = False if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) #绘制血槽 pygame.draw.line(screen,BLACK,(each.rect.left,each.rect.top-5)\ ,(each.rect.right,each.rect.top-5),2) #当生命值大于30%显示绿色,否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.3: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen,energy_color,(each.rect.left,each.rect.top-5)\ ,(each.rect.left+each.rect.width*energy_remain,each.rect.top-5),2) #即将出现在画面中,播放音效 if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: #毁灭 if not (delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 each.reset() #绘制中型敌机 for each in mid_enemies: if each.active: each.move() if each.hit: #如果被击中中,绘制击中特效 screen.blit(each.image_hit, each.rect) each.hit = False screen.blit(each.image, each.rect) #绘制血槽 pygame.draw.line(screen,BLACK,(each.rect.left,each.rect.top-5)\ ,(each.rect.right,each.rect.top-5),2) #当生命值大于40%显示绿色,否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.4: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen,energy_color,(each.rect.left,each.rect.top-5)\ ,(each.rect.left+each.rect.width*energy_remain,each.rect.top-5),2) else: #毁灭 if not (delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 each.reset() #被打死了回炉重造233 #绘制小型敌机 for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: #毁灭 if not (delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() #被打死了回炉重造233 #检测我方飞机是否被撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down: if not me.invincible: me.active = False for e in enemies_down: e.active = False #绘制我方飞机 if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: #毁灭 if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) #切换图片增加动效 if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 #绘制全屏炸弹数量 bomb_text = bomb_font.render('x %d' % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - bomb_rect.height - 10)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) #绘制剩余生命数量 for i in range(life_num): screen.blit(life_image, ((width - 10 - (i + 1) * life_rect.width), (height - 10 - life_rect.height))) #绘制分数 score_text = score_font.render('Score : %s' % str(score), True, WHITE) screen.blit(score_text, (10, 5)) #绘制游戏结束画面 elif life_num == 0: pygame.mixer.music.stop() pygame.mixer.stop() pygame.time.set_timer(SUPPLY_TIME, 0) #读取历史最高得分 if not recorded: recorded = True with open('recorder.txt', 'r') as f: record_score = int(f.read()) f.close() #如果玩家得分高于最高分,则存档 if score > record_score: f = open('recorder.txt', 'w') f.write(str(score)) f.close() #绘制结束界面 record_score_text = score_font.render("Best : %d" % record_score, True, (255, 255, 255)) screen.blit(record_score_text, (50, 50)) gameover_text1 = gameover_font.render("Your Score", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = \ (width - again_rect.width) // 2, \ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) # 检测用户的鼠标操作 # 如果用户按下鼠标左键 if pygame.mouse.get_pressed()[0]: # 获取鼠标坐标 pos = pygame.mouse.get_pos() # 如果用户点击“重新开始” if again_rect.collidepoint(pos): # 调用main函数,重新开始游戏 main() # 如果用户点击“结束游戏” elif gameover_rect.collidepoint(pos): # 退出游戏 pygame.quit() sys.exit() #绘制暂停按钮 screen.blit(paused_image, paused_rect) pygame.display.flip() clock.tick(60)
def main(): #pygame.mixer.music.play(重复次数,开始时间),这里重复次数会加上原来的一次,开始时间如果为1.0的话,表示从音乐的第2秒开始播放. pygame.mixer.music.play(-1) #这里设置-1表示无限循环 #生成我方飞机 me = MyPlane.MyPlane(bg_size) #生成敌方飞机 enemies = pygame.sprite.Group() #建立一个组 #生成敌方小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) #生成敌方中型飞机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) #生成敌方大型飞机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) #生成子弹 bullet1 = [] bullet1_index = 0 #用于索引 BULLET1_MUN = 6 #6颗子弹 for i in range(BULLET1_MUN): bullet1.append(bullet.Bullet1(me.rect.midtop)) #midtop是顶部中央的意思 #增强弹药 bullet2 = [] bullet2_index = 0 #用于索引 BULLET2_MUN = 12 #12颗子弹 for i in range(BULLET2_MUN // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) # 中弹图片索引 e1_des_index = 0 e2_des_index = 0 e3_des_index = 0 me_des_index = 0 #统计得分 score = 0 score_font = pygame.font.Font("font/font.TTF", 36) #定义字体 #标志是否暂停游戏 paused = False #加载暂停图片 stopping_img = pygame.image.load("image/stopping.png").convert_alpha() stopping_rect = stopping_img.get_rect() stopping_rect.left, stopping_rect.top = width / 2 - stopping_rect.width / 2, height / 2 - stopping_rect.height / 2 stop1_img = pygame.image.load("image/stop1.png").convert_alpha() stop2_img = pygame.image.load("image/stop2.png").convert_alpha() begin1_img = pygame.image.load("image/begin1.png").convert_alpha() begin2_img = pygame.image.load("image/begin2.png").convert_alpha() stop_rect = stop1_img.get_rect() begin_rect = begin1_img.get_rect() paused_rect = stop1_img.get_rect() stop_rect.left, stop_rect.top = width - stop_rect.width - 10, 10 begin_rect.left, begin_rect.top = width - begin_rect.width - 10, 10 pause_img = stop1_img #设置默认图片 #设置难度级别,默认难度1 level = 1 #全屏炸弹 bomb_img = pygame.image.load("image/boom.jpg").convert_alpha() bomb_rect = bomb_img.get_rect() bomb_font = pygame.font.Font("font/font.TTF", 48) bomb_num = 3 #炸弹数量 #每30秒发放一个补给56 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) #定时器 SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) #弹药增强定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 #标志是否使用增强弹药 is_double_bullet = False #生命数量 life_img = pygame.image.load("image/life.png").convert_alpha() life_rect = life_img.get_rect() life_num = 3 running = True switch_image = True #飞机图片切换 delay = 100 #人工干预延迟 #解除我方无敌状态计时器 INVINCIBLE_TIME = USEREVENT + 2 #用于重复打开文件 record_file = False #用于游戏结束界面 gameover_font = pygame.font.Font("font/font.TTF", 48) gameover_font1 = pygame.font.Font("font/font.TTF", 35) again_img = pygame.image.load("image/again.png").convert_alpha() #再来一次按钮 again_rect = again_img.get_rect() gameover_img = pygame.image.load( "image/gameover.png").convert_alpha() #结束游戏按钮 gameover_rect = gameover_img.get_rect() again_rect.left, again_rect.top = 318 + 65, 424 + 200 gameover_rect.left, gameover_rect.top = 318, 424 + 300 #标志是否超过历史最高分 is_congratulate = False #返回主菜单按钮 comeback1_img = pygame.image.load( "image/comeback1.png").convert_alpha() #返回按钮 comeback2_img = pygame.image.load("image/comeback2.png").convert_alpha() comeback_img = comeback1_img #设置默认图片 comeback_rect = comeback1_img.get_rect() comeback_rect.left, comeback_rect.top = 901 - 100, 897 - 100 while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() #检测玩家是否按下了暂停按钮 elif event.type == MOUSEBUTTONDOWN: if life_num: #collidepoint(event.pos),自动检测鼠标是否停留在pos内,如果是则返回True if event.button == 1 and paused_rect.collidepoint( event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) #定时器暂停 pygame.mixer.music.pause() #背景音乐暂停 pygame.mixer.pause() #所有其他音乐特效暂停 else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) #定时器开始 pygame.mixer.music.unpause() #背景音乐开始 pygame.mixer.unpause() #所有其他音乐特效开始 if life_num == 0: #检测玩家是否按下了退出游戏按钮 if event.button == 1 and gameover_rect.collidepoint( event.pos): pygame.quit() sys.exit() elif event.button == 1 and again_rect.collidepoint( event.pos): main() elif event.button == 1 and comeback_rect.collidepoint( event.pos): menu_sound.play() Menu() #检测鼠标是否移动到暂停游戏按钮 elif event.type == MOUSEMOTION: if life_num == 0: if event.type == MOUSEMOTION: if comeback_rect.collidepoint(event.pos): comeback_img = comeback1_img else: comeback_img = comeback2_img else: if paused_rect.collidepoint(event.pos): if paused: pause_img = begin2_img paused_rect = begin_rect else: pause_img = stop2_img paused_rect = stop_rect else: if paused: pause_img = begin1_img paused_rect = begin_rect else: pause_img = stop1_img paused_rect = stop_rect #引爆炸弹 elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb.play() for each in enemies: if each.rect.bottom > 0: each.active = False #规定时间发放补给56 elif event.type == SUPPLY_TIME: supply_sound.play() if choice([False, True]): bomb_supply.reset() else: bullet_supply.reset() #检测是否为增强弹药时间 elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) #关闭定时器 #无敌时间 elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) #根据玩家得分增加难度 #提升到难度2 if level == 1 and score >= 300: level = 2 up_level.play() #增加3架小敌机,2架中敌机和1架大敌机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) #提升敌机的速度 inc_speed(small_enemies, 1) #提升到难度3 elif level == 2 and score >= 800: level = 3 up_level.play() #增加5架小敌机,3架中敌机和1架大敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 1) #提升敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) #提升到难度4 elif level == 3 and score >= 1500: level = 4 up_level.play() #增加5架小敌机,3架中敌机和2架大敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) inc_speed(big_enemies, 1) #提升到难度5 elif level == 4 and score >= 2500: level = 5 up_level.play() #增加5架小敌机,3架中敌机和2架大敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) inc_speed(big_enemies, 1) screen.blit(background, (0, 0)) #显示背景 if paused: #显示暂停时的界面 screen.blit(stopping_img, stopping_rect) screen.blit(pause_img, paused_rect) #显示分数,Ture表示不显示锯齿 score_text = score_font.render("Score : %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) #在页面左上角显示分数 if life_num and not paused: #检测键盘事件 key_pressed = pygame.key.get_pressed() #包涵所有键盘事件的布尔值 #飞机移动 if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() #绘制炸弹补给并检测玩家是否获得补给56 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): #检测我方飞机是否与补给非透明部分碰撞 get_supply.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False #绘制子弹补给并检测玩家是否获得补给56 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): #检测我方飞机是否与补给非透明部分碰撞 bullet_supply.active = False get_supply.play() is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) #发射子弹 if not (delay % 10): #播放子弹的声音 if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_MUN else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_MUN #检测子弹是否击中敌机 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: e.hit = True e.energy -= 1 if e in mid_enemies or big_enemies: if not e.energy: e.active = False else: e.active = False #绘制大型敌机 for each in big_enemies: if each.active: each.move() if each.hit: #绘制被打到的画面 screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) #绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) #当生命大于30%时显示绿色血条,否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.3: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) #即将出现在画面中出现的音效 if each.rect.bottom == -50: big_enemy.play(-1) else: #毁灭 if not (delay % 3): if e3_des_index == 0: big_die.play() #播放死亡音效 screen.blit(each.destroy_images[e3_des_index], each.rect) e3_des_index = (e3_des_index + 1) % 6 if e3_des_index == 0: big_enemy.stop() score += 100 each.reset() #绘制中型敌机 for each in mid_enemies: if each.active: each.move() if each.hit: #绘制被打到的画面 screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) #绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) #当生命大于30%显示绿色,否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.3: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) else: #毁灭 if not (delay % 3): if e2_des_index == 0: big_die.play() #播放死亡音效 screen.blit(each.destroy_images[e2_des_index], each.rect) e2_des_index = (e2_des_index + 1) % 4 if e2_des_index == 0: score += 60 each.reset() #绘制小型敌机 for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: #毁灭 #big_die.play()#播放死亡音效 if not (delay % 3): screen.blit(each.destroy_images[e1_des_index], each.rect) e1_des_index = (e1_des_index + 1) % 4 if e1_des_index == 0: score += 10 each.reset() #检测我方飞机是否被撞,并自定义碰撞类型 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False #绘制我方飞机 if me.active: screen.blit(me.image, me.rect) else: #毁灭 #big_die.play()#播放死亡音效 if not (delay % 3): if me_des_index == 0: big_die.play() screen.blit(me.destroy_images[me_des_index], me.rect) me_des_index = (me_des_index + 1) % 5 if me_des_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) #绘制剩余炸弹数量 bomb_text = bomb_font.render("x %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_img, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) #绘制生命数量 if life_num: for i in range(life_num): screen.blit(life_img, (width - 10 - (i + 1) * life_rect.width, height - 10 - life_rect.height)) #显示分数,Ture表示不显示锯齿 score_text = score_font.render("Score : %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) #在页面左上角显示分数 #绘制暂停按钮 #print(paused_rect) screen.blit(pause_img, (797, 10)) #控制延迟切换图片 if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 #绘制游戏结束界面 elif life_num == 0: #背景音乐停止 pygame.mixer.music.stop() #停住全部音效 pygame.mixer.stop() #停止发放补给 pygame.time.set_timer(SUPPLY_TIME, 0) if not record_file: record_file = True #读取历史最高分 with open("record.txt", "r") as f: record_score = int(f.read()) if score > record_score: img_num = randint(1, 322) img_num1 = "image2/" + str(img_num) + ".jpg" #print(img_num1) with open(img_num1, "rb") as g: img_data = g.read() with open("img_num1.jpg", "wb") as g: g.write(img_data) score_best = gameover_font.render( "Best Score: %s" % str(score), True, WHITE) congratulate = gameover_font1.render( "Congratulations on your record!", True, WHITE) is_congratulate = True #标志是否超过历史最高分 con_rect = congratulate.get_rect() con_rect.left, con_rect.top = 264 - 50, 486 - 200 #print(con_rect.left, con_rect.top)264 486 #将记录保存到文件中 with open("record.txt", "w") as f: f.write(str(score)) else: score_best = gameover_font.render( "Best Score: %s" % str(record_score), True, WHITE) gameover_text = gameover_font.render("Game over!", True, WHITE) gameover_text_rect = gameover_text.get_rect() gameover_text_rect.left, gameover_text_rect.top = 318, 424 #print(gameover_text_rect.left, gameover_text_rect.top)318 424 your_score = gameover_font.render("Your Score: %s" % str(score), True, WHITE) #绘制结束画面 if is_congratulate: screen.blit(congratulate, con_rect) screen.blit(again_img, again_rect) screen.blit(gameover_img, gameover_rect) screen.blit(score_best, (20, 20)) screen.blit(your_score, (20, 80)) screen.blit(gameover_text, gameover_text_rect) screen.blit(comeback_img, comeback_rect) pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) #-1表示循环播放 #生成我方飞机 me = myplane.MyPlane(bg_size) enemies = pygame.sprite.Group() #所有敌机群体 #生成敌方小飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) #生成敌方中飞机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) #生成敌方大飞机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) #生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 #估计4颗子弹就能占据频幕80%长度 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) #生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 33, me.rect.centery))) clock = pygame.time.Clock() #中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 #统计得分 score = 0 score_font = pygame.font.Font('font/font.ttf', 36) #字体及大小 #游戏说明 readme_font = pygame.font.Font('font/font.ttf', 24) #标志是否暂停游戏 paused = False pause_nor_image = pygame.image.load('images/pause_nor.png').convert_alpha() pause_pressed_image = pygame.image.load( 'images/pause_pressed.png').convert_alpha() resume_nor_image = pygame.image.load( 'images/resume_nor.png').convert_alpha() resume_pressed_image = pygame.image.load( 'images/resume_pressed.png').convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image #设置默认图片 #设置难度级别 level = 1 #全屏炸弹 bomb_image = pygame.image.load('images/bomb.png').convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font('font/font.ttf', 48) bomb_num = 3 #每30秒发放一个补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT #自定义事件 pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) #超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 #标志是否使用超级子弹 is_double_bullet = False #解除我方无敌状态定时器 INVINCIBLE_TIME = USEREVENT + 2 #生命数量 life_image = pygame.image.load('images/life.png').convert_alpha() life_rect = life_image.get_rect() life_num = 3 #用于限制重复打开记录文件 recorded = False #游戏结束界面 gameover_font = pygame.font.Font('font/font.ttf', 48) again_image = pygame.image.load('images/again.png').convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load('images/gameover.png').convert_alpha() gameover_rect = gameover_image.get_rect() #用于切换图片 switch_image = True #用于延迟 delay = 100 running = True while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: #检测鼠标是否点击按钮 if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) #暂停时取消自定义事件 pygame.mixer.music.pause() #暂停背景音乐 pygame.mixer.pause() #暂停所有音效 else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) #恢复事件 pygame.mixer.music.unpause() #恢复背景音乐 pygame.mixer.unpause() #恢复所有音效 #重新开始游戏 if event.button == 1 and again_rect.collidepoint(event.pos): life_num = 3 score = 0 pygame.mixer.music.play() pygame.mixer.init() pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) #初始化敌机 for each in enemies: each.reset() #初始化我方飞机 me.reset() #游戏结束退出 if event.button == 1 and gameover_rect.collidepoint(event.pos): pygame.quit() sys.exit() #检测鼠标指针是否在按钮上 elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image #全屏炸弹效果 elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() #补给到来提示音 #随机投放一种补给 if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) #根据得分增加难度 if level == 1 and score > 50000: level = 2 upgrade_sound.play() #增加3架小型敌机2架中型敌机和1架大型敌机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) #提升小型敌机的速度 inc_speed(small_enemies, 1) elif level == 2 and score > 300000: level = 3 upgrade_sound.play() #增加5架小型敌机3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升小型敌机的速度 inc_speed(small_enemies, 1) #提升中型敌机的速度 inc_speed(mid_enemies, 1) elif level == 3 and score > 600000: level = 4 upgrade_sound.play() #增加5架小型敌机3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升小型敌机的速度 inc_speed(small_enemies, 1) #提升中型敌机的速度 inc_speed(mid_enemies, 1) elif level == 4 and score > 1000000: level = 5 upgrade_sound.play() #增加5架小型敌机3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升小型敌机的速度 inc_speed(small_enemies, 1) #提升中型敌机的速度 inc_speed(mid_enemies, 1) screen.blit(background, (0, 0)) if paused: f = open('readme.txt', 'r') f.readline() y = 100 for each in f: line = each.split('\n')[0] line_txt = readme_font.render(line, True, WHITE) screen.blit(line_txt, (30, y)) y += 40 #主流程 if life_num and not paused: #检测用户的键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() #绘制全屏炸弹补给并检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False #绘制超级子弹补给并检测是否获得 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() #发射超级子弹18秒 is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False #绘制子弹,10帧一射 if not (delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 33, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM #检测子弹是否击中敌机 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False #绘制大型敌机 for each in big_enemies: #判断是否存活 if each.active: each.move() if each.hit: #绘制被击中的样子 screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) #绘制血槽 pygame.draw.line(screen,BLACK,\ (each.rect.left,each.rect.top - 5),\ (each.rect.right,each.rect.top - 5),\ 2) #当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen,energy_color,\ (each.rect.left,each.rect.top -5),\ (each.rect.left + each.rect.width * energy_remain,\ each.rect.top -5),\ 2) #即将出现在画面中,播放音效 if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: #毁灭 if not (delay % 3): #只播放一次音效 if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 #小技巧,只取0到5 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 each.reset() #绘制中型敌机 for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) #绘制血槽 pygame.draw.line(screen,BLACK,\ (each.rect.left,each.rect.top - 5),\ (each.rect.right,each.rect.top - 5),\ 2) #当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen,energy_color,\ (each.rect.left,each.rect.top -5),\ (each.rect.left + each.rect.width * energy_remain,\ each.rect.top -5),\ 2) else: #毁灭 if not (delay % 3): #只播放一次音效 if e1_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e3_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 each.reset() #绘制小型敌机 for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: #毁灭 if not (delay % 3): #只播放一次音效 if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() #检测我方飞机是否被撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False #绘制我方飞机 switch_image = not switch_image if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: #毁灭 if not (delay % 3): #只播放一次音效 if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) #3秒无敌 #绘制全屏炸弹剩余数量 bomb_text = bomb_font.render('X %d' % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) #绘制剩余生命数量 if life_num: for i in range(life_num): screen.blit(life_image,\ (width-10-(i+1)*life_rect.width,\ height-10-life_rect.height)) #绘制得分,将文字渲染成surface对象 score_text = score_font.render('score: %s' % str(score), True, WHITE) screen.blit(score_text, (10, 5)) #绘制游戏结束画面 elif life_num == 0: #背景音乐停止 pygame.mixer.music.stop() #停止全部音效 pygame.mixer.stop() #停止发放补给 pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True #读取历史最高分 with open('record.txt') as f: record_score = int(f.read()) #如果玩家得分高于历史最高,则存档 if score > record_score: with open('record.txt', 'w') as f: f.write(str(score)) #绘制结束界面 record_score_text = score_font.render('Best : %d' % record_score, True, WHITE) screen.blit(record_score_text, (25, 25)) gameover_text1 = gameover_font.render('Your score', True, WHITE) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left,gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2,\ height // 2 - 100 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, WHITE) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left,gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2,\ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left,again_rect.top = \ (width - again_rect.width) // 2,\ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left,gameover_rect.top = \ (width - again_rect.width) // 2,\ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) #绘制暂停按钮 screen.blit(paused_image, paused_rect) #切换图片(利用延迟) if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) # �����ҷ��ɻ� me = myplane.MyPlane(bg_size) enemies = pygame.sprite.Group() # ���ɵз�С�ͷɻ� small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) # ���ɵз����ͷɻ� mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) # ���ɵз����ͷɻ� big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) # ������ͨ�ӵ� bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # ���ɳ����ӵ� bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM//2): bullet2.append(bullet.Bullet2((me.rect.centerx-33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx+30, me.rect.centery))) clock = pygame.time.Clock() # �е�ͼƬ���� e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 # ͳ�Ƶ÷� score = 0 score_font = pygame.font.Font("font/font.ttf", 36) # ��־�Ƿ���ͣ��Ϸ paused = False pause_nor_image = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load("images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load("images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load("images/resume_pressed.png").convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image # �����Ѷȼ��� level = 1 # ȫ��ը�� bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 # ÿ30�뷢��һ�������� bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) # �����ӵ���ʱ�� DOUBLE_BULLET_TIME = USEREVENT + 1 # ��־�Ƿ�ʹ�ó����ӵ� is_double_bullet = False # ����ҷ���״̬��ʱ�� INVINCIBLE_TIME = USEREVENT + 2 # �������� life_image = pygame.image.load("images/life.png").convert_alpha() life_rect = life_image.get_rect() life_num = 3 # ������ֹ�ظ���¼�ļ� recorded = False # ��Ϸ�������� gameover_font = pygame.font.Font("font/font.TTF", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() # �����л�ͼƬ switch_image = True # �����ӳ� delay = 100 running = True while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) # �����û��ĵ÷������Ѷ� if level == 1 and score > 50000: level = 2 upgrade_sound.play() # ����3��С�͵л���2�����͵л���1�ܴ��͵л� add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) # ����С�͵л����ٶ� inc_speed(small_enemies, 1) elif level == 2 and score > 300000: level = 3 upgrade_sound.play() # ����5��С�͵л���3�����͵л���2�ܴ��͵л� add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # ����С�͵л����ٶ� inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 3 and score > 600000: level = 4 upgrade_sound.play() # ����5��С�͵л���3�����͵л���2�ܴ��͵л� add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # ����С�͵л����ٶ� inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 4 and score > 1000000: level = 5 upgrade_sound.play() # ����5��С�͵л���3�����͵л���2�ܴ��͵л� add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # ����С�͵л����ٶ� inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) screen.blit(background, (0, 0)) if life_num and not paused: # ����û��ļ��̲��� key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() # ����ȫ��ը������������Ƿ��� if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False # ���Ƴ����ӵ�����������Ƿ��� if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False # �����ӵ� if not(delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset((me.rect.centerx-33, me.rect.centery)) bullets[bullet2_index+1].reset((me.rect.centerx+30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM # ����ӵ��Ƿ���ел� for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide(b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False # ���ƴ��͵л� for each in big_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) # ����Ѫ�� pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # ����������20%��ʾ��ɫ��������ʾ��ɫ energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) # ���������ڻ����У�������Ч if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: # ���� if not(delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 each.reset() # �������͵л��� for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # ����Ѫ�� pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # ����������20%��ʾ��ɫ��������ʾ��ɫ energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) else: # ���� if not(delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 each.reset() # ����С�͵л��� for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: # ���� if not(delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() # ����ҷ��ɻ��Ƿ�ײ enemies_down = pygame.sprite.spritecollide(me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False # �����ҷ��ɻ� if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: # ���� if not(delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) # ����ȫ��ը������ bomb_text = bomb_font.render("�� %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # ����ʣ���������� if life_num: for i in range(life_num): screen.blit(life_image, \ (width-10-(i+1)*life_rect.width, \ height-10-life_rect.height)) # ���Ƶ÷� score_text = score_font.render("Score : %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) # ������Ϸ�������� elif life_num == 0: # ��������ֹͣ pygame.mixer.music.stop() # ֹͣȫ����Ч pygame.mixer.stop() # ֹͣ���Ų��� pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True # ��ȡ��ʷ��ߵ÷� with open("record.txt", "r") as f: record_score = int(f.read()) # �����ҵ÷ָ�����ʷ��ߵ÷֣���浵 if score > record_score: with open("record.txt", "w") as f: f.write(str(score)) # ���ƽ������� record_score_text = score_font.render("Best : %d" % record_score, True, (255, 255, 255)) screen.blit(record_score_text, (50, 50)) gameover_text1 = gameover_font.render("Your Score", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = \ (width - again_rect.width) // 2, \ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) # ����û��������� # ����û����������� if pygame.mouse.get_pressed()[0]: # ��ȡ������� pos = pygame.mouse.get_pos() # ����û���������¿�ʼ�� if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: # ����main���������¿�ʼ��Ϸ main() # ����û������������Ϸ�� elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: # �˳���Ϸ pygame.quit() sys.exit() # ������ͣ��ť screen.blit(paused_image, paused_rect) # �л�ͼƬ if not(delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(USER): pygame.init() pygame.mixer.init() bg_size = width, height = 480, 700 screen = pygame.display.set_mode(bg_size) pygame.display.set_caption('Plane War') # background = pygame.image.load(MAINFILE_PATH + 'images/img_bg_level_1.jpg').convert() # 定义颜色 BLACK = (0, 0, 0) GREEN = (0, 255, 0) RED = (255, 0, 0) WHITE = (255, 255, 255) # 载入音乐 pygame.mixer.music.load(MAINFILE_PATH + 'sound/hundouluo.wav') pygame.mixer.music.set_volume(0.2) bullet_sound = pygame.mixer.Sound(MAINFILE_PATH + 'sound/bullet.wav') bullet_sound.set_volume(0.2) bomb_sound = pygame.mixer.Sound(MAINFILE_PATH + 'sound/use_bomb.wav') bomb_sound.set_volume(0.2) supply_sound = pygame.mixer.Sound(MAINFILE_PATH + 'sound/supply.wav') supply_sound.set_volume(0.2) get_bomb_sound = pygame.mixer.Sound(MAINFILE_PATH + 'sound/get_bomb.wav') get_bomb_sound.set_volume(0.2) get_bullet_sound = pygame.mixer.Sound(MAINFILE_PATH + 'sound/get_bullet.wav') get_bullet_sound.set_volume(0.2) upgrade_sound = pygame.mixer.Sound(MAINFILE_PATH + 'sound/upgrade.wav') upgrade_sound.set_volume(0.2) enemy3_fly_sound = pygame.mixer.Sound(MAINFILE_PATH + 'sound/enemy3_flying.wav') enemy3_fly_sound.set_volume(0.6) enemy1_down_sound = pygame.mixer.Sound(MAINFILE_PATH + 'sound/enemy1_down.wav') enemy1_down_sound.set_volume(0.2) enemy2_down_sound = pygame.mixer.Sound(MAINFILE_PATH + 'sound/enemy2_down.wav') enemy2_down_sound.set_volume(0.2) enemy3_down_sound = pygame.mixer.Sound(MAINFILE_PATH + 'sound/enemy3_down.wav') enemy3_down_sound.set_volume(0.2) me_down_sound = pygame.mixer.Sound(MAINFILE_PATH + 'sound/me_down.wav') me_down_sound.set_volume(0.2) def add_small_enemies(group1, group2, num): for i in range(num): e1 = enemy.SmallEnemy(bg_size) group1.add(e1) group2.add(e1) def add_mid_enemies(group1, group2, num): for i in range(num): e2 = enemy.MidEnemy(bg_size) group1.add(e2) group2.add(e2) def add_big_enemies(group1, group2, num): for i in range(num): e3 = enemy.BigEnemy(bg_size) group1.add(e3) group2.add(e3) def inc_speed(target, inc): for each in target: each.speed += inc def add_background(background_image, screen): bg1 = Background(background_image, screen) bg2 = Background(background_image, screen, True) background_group = pygame.sprite.Group(bg1, bg2) return background_group # 播放音乐 pygame.mixer.music.play(-1) # 第一关背景 background_group = add_background( MAINFILE_PATH + 'images/img_bg_level_1.jpg', screen) # 关卡锁 level_2 = False level_3 = False level_4 = False level_5 = False # 实例我方飞机 me = myplane.MyPlane(bg_size=bg_size) # 实例敌方飞机 enemies = pygame.sprite.Group() # 实例敌方小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 10) # 实例敌方中型飞机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) # 实例敌方大型飞机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) # 实例普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 6 for i in range(BULLET1_NUM): bullet1.append( bullet.Bullet1((me.rect.centerx - 10, me.rect.centery), screen)) # 实例超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 10 for i in range(BULLET2_NUM // 2): bullet2.append( bullet.Bullet2((me.rect.centerx - 33, me.rect.centery), screen)) bullet2.append( bullet.Bullet2((me.rect.centerx + 30, me.rect.centery), screen)) # 中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 # 统计得分 score = 0 score_font = pygame.font.Font(MAINFILE_PATH + "font/rough.ttf", 36) # 标志是否暂停游戏 paused = False paused_nor_image = pygame.image.load( MAINFILE_PATH + "images/pause_nor.png").convert_alpha() paused_pressed_image = pygame.image.load( MAINFILE_PATH + "images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load( MAINFILE_PATH + 'images/resume_nor.png').convert_alpha() resume_pressed_image = pygame.image.load( MAINFILE_PATH + 'images/resume_pressed.png').convert_alpha() paused_rect = paused_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = paused_nor_image # 设置难度 level = 1 # 全屏炸弹 bomb_image = pygame.image.load(MAINFILE_PATH + 'images/bomb.png').convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font(MAINFILE_PATH + "font/font.ttf", 48) bomb_num = 3 # 每30秒发放一个补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 15 * 1000) # 超级子弹定时器 DOUBLE_BULLTET_TIME = USEREVENT + 1 # 解除我方重生无敌定时器 INVINCIBLE_TIME = USEREVENT + 2 # 标志是否使用超级子弹 is_double_bullet = False # 生命数量 life_image = pygame.image.load(MAINFILE_PATH + 'images/My_plane.png').convert_alpha() life_width, life_height = life_image.get_size() life_width, life_height = life_width // 4, life_height // 4 life_image = pygame.transform.smoothscale(life_image, (life_width, life_height)) life_rect = life_image.get_rect() life_num = 3 # 游戏结束画面 gameover_font = pygame.font.Font(MAINFILE_PATH + "font/font.TTF", 48) again_image = pygame.image.load(MAINFILE_PATH + "images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load(MAINFILE_PATH + "images/gameexit.png").convert_alpha() gameover_rect = gameover_image.get_rect() # 用于延迟切换 delay = 100 # 限制打开一次记录文件 recorded = False clock = pygame.time.Clock() running = True while running: if not pygame.display.get_active(): paused = True pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() # if pygame.display.get_active(): # paused = False for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 15 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = paused_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = paused_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.key == K_p: paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 15 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.key == K_ESCAPE: pygame.quit() sys.exit() elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLTET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLTET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) # 根据用户得分增加难度 if level == 1 and score > 1000: level = 2 if not level_2: background_group.empty() background_group = add_background( MAINFILE_PATH + 'images/img_bg_level_2.jpg', screen) level_2 = True upgrade_sound.play() # 增加3架小型敌机, 2架中型敌机和1架大型敌机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) # 提升小型敌机的速度 inc_speed(target=small_enemies, inc=1) elif level == 2 and score > 3000: level = 3 if not level_3: background_group.empty() background_group = add_background( MAINFILE_PATH + 'images/img_bg_level_3.jpg', screen) level_3 = True upgrade_sound.play() # 增加5架小型敌机, 3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升小型敌机的速度 inc_speed(target=small_enemies, inc=1) inc_speed(target=mid_enemies, inc=1) elif level == 3 and score > 10000: level = 4 if not level_4: background_group.empty() background_group = add_background( MAINFILE_PATH + 'images/img_bg_level_4.jpg', screen) level_4 = True upgrade_sound.play() # 增加5架小型敌机, 3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升小型敌机的速度 inc_speed(target=small_enemies, inc=1) inc_speed(target=mid_enemies, inc=1) elif level == 4 and score > 20000: level = 5 if not level_5: background_group.empty() background_group = add_background( MAINFILE_PATH + 'images/img_bg_level_5.jpg', screen) level_5 = True upgrade_sound.play() # 增加5架小型敌机, 3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # 提升小型敌机的速度 inc_speed(target=small_enemies, inc=1) inc_speed(target=mid_enemies, inc=1) inc_speed(target=big_enemies, inc=1) # screen.blit(background, (0, 0)) background_group.update() background_group.draw(screen) if life_num and not paused: # 检测键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() # if key_pressed[K_p]: # paused = not paused # pygame.time.set_timer(SUPPLY_TIME, 0) # pygame.mixer.music.pause() # pygame.mixer.pause() # 绘制全屏炸弹补给 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(me, bomb_supply): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False # 绘制超级子弹补给 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(me, bullet_supply): get_bullet_sound.play() # 发射超级子弹 is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLTET_TIME, 8 * 1000) bullet_supply.active = False # 发射子弹 if not (delay % 16): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset( (me.rect.centerx - 10, me.rect.centery)) bullet1_index = (bullet1_index + 1) % BULLET1_NUM # 检测子弹是否击中敌机 try: for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for each in enemy_hit: each.hit = True each.energy -= 1 if each.energy == 0: each.active = False except: pass # 绘制敌方大型机 for each in big_enemies: if each.active: each.move() screen.blit(each.image, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) # 当生命大于20%显示绿色, 否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line( screen, energy_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) # 即将出现在画面, 播放音效 if each.rect.bottom == -10: enemy3_fly_sound.play(-1) each.appear = True # 离开画面, 关闭音效 if each.rect.bottom < -10 and each.appear: enemy3_fly_sound.stop() each.appear = False else: # 毁灭 if e3_destroy_index == 0: enemy3_down_sound.play() if not (delay % 2): screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 1000 each.reset() # 绘制敌方中型机 for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) # 当生命大于20%显示绿色, 否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line( screen, energy_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) else: # 毁灭 if e2_destroy_index == 0: enemy2_down_sound.play() if not (delay % 2): screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 600 each.reset() # 绘制敌方小型机 for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: # 毁灭 if e1_destroy_index == 0: enemy1_down_sound.play() if not (delay % 2): screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 100 each.reset() # 检测我方飞机碰撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for each in enemies_down: each.active = False # 绘制我方飞机 if me.active: screen.blit(me.image, me.rect) else: # 毁灭 if me_destroy_index == 0: me_down_sound.play() if not (delay % 2): screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) # 绘制全屏炸弹数量 bomb_text = bomb_font.render("× %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # 绘制剩余生命数量 if life_num: for i in range(life_num): screen.blit(life_image, ((width - 10 - (i + 1) * life_rect.width), height - 10 - life_rect.height)) # 绘制得分 score_text = score_font.render('Score : %d' % score, True, WHITE) screen.blit(score_text, (10, 5)) # elif life_num and paused: # key_pressed = pygame.key.get_pressed() # if key_pressed[K_p]: # paused = not paused # pygame.time.set_timer(SUPPLY_TIME, 15 * 1000) # pygame.mixer.music.unpause() # pygame.mixer.unpause() # 绘制游戏结束画面 elif life_num == 0: # 背景音乐停止 pygame.mixer.music.stop() # 停止全部音效 pygame.mixer.stop() # 停止发放补给 pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True # 读取历史最高分 try: with open('record.txt', 'r') as f: record = f.read() record_user = record.split(',')[0] record_score = int(record.split(',')[1]) # 判断是否高于历史最高分 if score > record_score: with open('record.txt', 'w') as f: f.write(USER + "," + str(score)) record_score = score record_user = USER except: with open('record.txt', 'w') as f: f.write(USER + "," + str(score)) record_score = score record_user = USER # 绘制结束界面 record_score_text = score_font.render("Best : %d" % record_score, True, (255, 255, 255)) screen.blit(record_score_text, (50, 50)) record_user_text = score_font.render("User : %s" % record_user, True, (255, 255, 255)) screen.blit(record_user_text, (200, 50)) gameover_text1 = gameover_font.render("Your Score", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = \ (width - again_rect.width) // 2, \ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) # 检测用户的鼠标操作 # 如果用户按下鼠标左键 if pygame.mouse.get_pressed()[0]: # 获取鼠标坐标 pos = pygame.mouse.get_pos() # 如果用户点击“重新开始” if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: # 调用main函数,重新开始游戏 main(USER) # 如果用户点击“结束游戏” elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: # 退出游戏 pygame.quit() sys.exit() # 绘制暂停按钮 screen.blit(paused_image, paused_rect) delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) # Tạo máy bay me = myplane.MyPlane(bg_size) enemies = pygame.sprite.Group() # tạo kẻ địch 1 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) # tạo kẻ địch 2 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) # tạo trùm cuối big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) # Đạn loại 1 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # Đạn loại 2 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) clock = pygame.time.Clock() # bị tiêu diệt e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 # Điểm thống kê score = 0 score_font = pygame.font.Font("font/font.ttf", 36) # Nút tạm dừng trò chơi paused = False pause_nor_image = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load( "images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load( "images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load( "images/resume_pressed.png").convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image # độ khó level = 2 # Skill bom bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 # 30s sẽ rót 1 item bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) # Thời gian phát nổ DOUBLE_BULLET_TIME = USEREVENT + 1 is_double_bullet = False INVINCIBLE_TIME = USEREVENT + 2 # Mạng life_image = pygame.image.load("images/life.png").convert_alpha() life_rect = life_image.get_rect() life_num = 3 # Ngăn ghi nhiều tệp recorded = False # Sau khi thua gameover_font = pygame.font.Font("font/font.TTF", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() # chuyển đổi ảnh switch_image = True # Độ trễ delay = 100 running = True while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) # Tăng độ khó dựa trên điểm người chơi if level == 1 and score > 500: level = 2 upgrade_sound.play() # Thêm 3 máy bay địch nhỏ, 2 máy bay địch trung bình và 1 máy bay địch lớn add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) # Tăng tốc độ của máy bay địch nhỏ inc_speed(small_enemies, 1) elif level == 2 and score > 6000: level = 3 upgrade_sound.play() # Thêm 5 máy bay địch nhỏ, 3 máy bay địch trung bình và 2 máy bay địch lớn add_small_enemies(small_enemies, enemies, 10) add_mid_enemies(mid_enemies, enemies, 4) add_big_enemies(big_enemies, enemies, 1) # Tăng tốc độ của máy bay địch nhỏ inc_speed(small_enemies, 2) inc_speed(mid_enemies, 1) elif level == 3 and score > 200000: level = 4 upgrade_sound.play() # Thêm 5 máy bay địch nhỏ, 3 máy bay địch trung bình và 2 máy bay địch lớn add_small_enemies(small_enemies, enemies, 15) add_mid_enemies(mid_enemies, enemies, 6) add_big_enemies(big_enemies, enemies, 2) # Tăng tốc độ của máy bay địch nhỏ inc_speed(small_enemies, 2) inc_speed(mid_enemies, 1) elif level == 4 and score > 1000000: level = 5 upgrade_sound.play() # Thêm 5 máy bay địch nhỏ, 3 máy bay địch trung bình và 2 máy bay địch lớn add_small_enemies(small_enemies, enemies, 20) add_mid_enemies(mid_enemies, enemies, 9) add_big_enemies(big_enemies, enemies, 3) # Tăng tốc độ của máy bay địch nhỏ inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) screen.blit(background, (0, 0)) if life_num and not paused: # Thao tác di chuyển key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() # Vẽ nguồn cung cấp bom toàn màn hình và kiểm tra xem chúng có lấy đc không(tối đa là 3 nha) if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False # Rút nguồn cung cấp đạn 2 và kiểm tra xem chúng có được không if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False # Bắn một viên đạn if not (delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM # Kiểm tra xem đạn có trúng máy bay địch không for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False # Tạo máy bay địch cỡ lớn for each in big_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) # Vẽ thanh máu pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # Máu lớn hơn 20% thì xanh ngược lại thì đỏ energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) # Xuất hiện sẽ có âm thanh if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: # Âm thanh khi bị tiêu diệt if not (delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 each.reset() # Vẽ máy bay địch cỡ trung bình : for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # Vẽ thanh máu pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # Máu lớn hơn 20% thì xanh ngược lại thì đỏ energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) else: # Âm thanh khi bị tiêu diệt if not (delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 each.reset() # Vẽ máy bay địch cỡ nhỏ : for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: # Âm thanh khi bị tiêu diệt if not (delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() # Kiểm tra trúng đạn enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False # Tạo máy bay chính if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: # Khi bị tiêu diệt if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) # Rút số lượng skill bom xài bomb_text = bomb_font.render("× %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # Điểm if life_num: for i in range(life_num): screen.blit(life_image, \ (width - 10 - (i + 1) * life_rect.width, \ height - 10 - life_rect.height)) # Xét score_text = score_font.render("Score : %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) # Đưa đến màn hình kết thúc trò chơi elif life_num == 0: # Nhạc nền pygame.mixer.music.stop() # Tắt âm pygame.mixer.stop() # Ngừng cung cấp pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True # Đọc điểm cao nhất trong lịch sử with open("record.txt", "r") as f: record_score = int(f.read()) # Nếu điểm của người chơi cao hơn điểm cao nhất trong lịch sử thì lưu if score > record_score: with open("record.txt", "w") as f: f.write(str(score)) # Tạo màn hình kết thúc record_score_text = score_font.render("Best : %d" % record_score, True, (255, 255, 255)) screen.blit(record_score_text, (50, 50)) gameover_text1 = gameover_font.render("Your Score", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = \ (width - again_rect.width) // 2, \ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) # Click chuột thì nó sẽ hiểu # Nếu người dùng nhấn nút chuột trái if pygame.mouse.get_pressed()[0]: # Nhận tọa độ chuột pos = pygame.mouse.get_pos() # Nếu người dùng nhấp vào "Chơi lại" if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: # Gọi chức năng chính để khởi động lại trò chơi main() # Nếu người dùng nhấp vào "among us" thì kết thúc trò chơi elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: # Thoát game pygame.quit() sys.exit() # Tạo nút pause screen.blit(paused_image, paused_rect) # Chuyển đổi hình ảnh if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) #生成我方飞机 me = myplane.MyPlane(bg_size) #生成敌方飞机 enemies = pygame.sprite.Group() #生成敌方小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) #生成敌方中型飞机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) #生成敌方大型飞机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) #生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) #生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) clock = pygame.time.Clock() #中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 #统计得分 score = 0 score_font = pygame.font.Font('font/font.ttf', 36) #暂停 paused = False pause_nor_image = pygame.image.load('images/pause_nor.png').convert_alpha() pause_pressed_image = pygame.image.load( 'images/pause_pressed.png').convert_alpha() resume_nor_image = pygame.image.load( 'images/resume_nor.png').convert_alpha() resume_pressed_image = pygame.image.load( 'images/resume_pressed.png').convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image #设置难度 level = 1 #全屏炸弹 bomb_image = pygame.image.load('images/bomb.png').convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font('font/font.ttf', 48) bomb_num = 3 #每一段时间出现补给 supply bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 8 * 1000) #超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 #标志是否使用超级子弹 is_double_bullet = False #无敌时间定时器 INVINCIBLE_TIME = USEREVENT + 2 #生命 life_image = pygame.image.load('images/life.png').convert_alpha() life_rect = life_image.get_rect() life_num = 3 #用于阻止重复打开记录文件 recorded = False #切换图片 switch_image = True #游戏结束画面 gameover_font = pygame.font.Font("font/font.ttf", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() #飞机尾气延时 delay = 100 running = True while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 8 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False me.invi() pygame.time.set_timer(INVINCIBLE_TIME, 1 * 1000) elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) #根据用户得分增加难度 if level == 1 and score >= 50000: level = 2 upgrade_sound.play() #增加3/2/1架 small_enemy/mid_enemy/big_enemy add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) #提升敌机速度 inc_speed(small_enemies, 0.5) elif level == 2 and score >= 300000: level = 3 upgrade_sound.play() #增加4/2/1架 small_enemy/mid_enemy/big_enemy add_small_enemies(small_enemies, enemies, 4) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) #提升敌机速度 inc_speed(small_enemies, 0.5) inc_speed(mid_enemies, 0.5) elif level == 3 and score >= 600000: level = 4 upgrade_sound.play() #增加4/3/1架 small_enemy/mid_enemy/big_enemy add_small_enemies(small_enemies, enemies, 4) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 1) #提升敌机速度 inc_speed(small_enemies, 0.5) inc_speed(mid_enemies, 0.5) inc_speed(big_enemies, 0.25) elif level == 4 and score >= 1000000: level = 5 upgrade_sound.play() #增加5/3/2架 small_enemy/mid_enemy/big_enemy add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升敌机速度 inc_speed(small_enemies, 0.5) inc_speed(mid_enemies, 0.5) inc_speed(big_enemies, 0.5) #绘制背景background 绘制代码不要随便变动代码位置 背景置底 screen.blit(background, (0, 0)) if life_num and not paused: #检测键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() #绘制全屏炸弹补给 检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 5: bomb_num += 1 bomb_supply.active = False #绘制超级子弹补给 检测是否获得 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() #发射超级子弹 is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False #发射子弹 if not (delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM #检测子弹是否击中敌方 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.energy -= 1 e.hit = True if e.energy == 0: e.active = False else: e.active = False #绘制敌方飞机 大型机 for each in big_enemies: if each.active: each.move() if each.hit: #绘制被打倒的特效 screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) #绘制血槽 pygame.draw.line(screen,BLACK,\ (each.rect.left,each.rect.top-5),\ (each.rect.right,each.rect.top-5),\ 2) #当生命大于50%显示绿色 50%-26%显示黄色 25%及以下显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.5: energy_color = GREEN elif energy_remain > 0.25: energy_color = YELLOW else: energy_color = RED pygame.draw.line(screen,energy_color,\ (each.rect.left,each.rect.top-5),\ (each.rect.left+each.rect.width*energy_remain,\ each.rect.top-5),\ 2) #即将出现在画面中播放音效 if each.rect.bottom == -50: enemy3_flying_sound.play(-1) else: #毁灭 if not (delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_flying_sound.stop() score += 50000 each.reset() #绘制敌方飞机 中型机 for each in mid_enemies: if each.active: each.move() if each.hit: #绘制被打倒的特效 screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) #绘制血槽 pygame.draw.line(screen,BLACK,\ (each.rect.left,each.rect.top-5),\ (each.rect.right,each.rect.top-5),\ 2) #当生命大于50%显示绿色 50%-26%显示黄色 25%及以下显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.5: energy_color = GREEN elif energy_remain > 0.25: energy_color = YELLOW else: energy_color = RED pygame.draw.line(screen,energy_color,\ (each.rect.left,each.rect.top-5),\ (each.rect.left+each.rect.width*energy_remain,\ each.rect.top-5),\ 2) else: #毁灭 if not (delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 20000 each.reset() #绘制敌方飞机 小型机 for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) #绘制血槽 pygame.draw.line(screen,BLACK,\ (each.rect.left,each.rect.top-5),\ (each.rect.right,each.rect.top-5),\ 2) #当生命大于50%显示绿色 50%-26%显示黄色 25%及以下显示红色 energy_remain = each.energy / enemy.SmallEnemy.energy if energy_remain > 0.5: energy_color = GREEN elif energy_remain > 0.25: energy_color = YELLOW else: energy_color = RED pygame.draw.line(screen,energy_color,\ (each.rect.left,each.rect.top-5),\ (each.rect.left+each.rect.width*energy_remain,\ each.rect.top-5),\ 2) else: #毁灭 if not (delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() #检测我方飞机是否被撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False #绘制我方飞机 if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: #毁灭 if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) #绘制剩余bomb数量 bomb_text = bomb_font.render('x %d' % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) #绘制剩余生命数量 if life_num: for i in range(life_num): screen.blit(life_image,\ (width-10-(i+1)*life_rect.width,\ height-10-life_rect.height)) #绘制得分 score_text = score_font.render('Score:%s' % str(score), True, WHITE) screen.blit(score_text, (10, 5)) #绘制游戏结束画面 elif life_num == 0: #停止bgm 音效 pygame.mixer.music.stop() pygame.mixer.stop() #停止发放补给 pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True #读取历史最高得分 with open('record.txt', 'r') as f: record_score = int(f.read()) #如果玩家得分高于历史最高得分,则存档 if score > record_score: with open('record.txt', 'w') as f: f.write(str(score)) #绘制结束界面 record_score_text = score_font.render('Best : %d' % record_score, True, (255, 255, 255)) screen.blit(record_score_text, (50, 50)) gameover_text1 = gameover_font.render('Your Score', True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left,again_rect.top=\ (width-again_rect.width)//2, \ gameover_text2_rect.bottom+50 screen.blit(again_image, again_rect) gameover_rect.left,gameover_rect.top=\ (width-again_rect.width)//2, \ again_rect.bottom+10 screen.blit(gameover_image, gameover_rect) #检测用户的鼠标操作 如果用户按下鼠标左键 if pygame.mouse.get_pressed()[0]: #获取鼠标坐标 pos = pygame.mouse.get_pos() #点击重新开始 if again_rect.left<pos[0]<again_rect.right and \ again_rect.top<pos[1]<again_rect.bottom: main() #点击结束游戏 if gameover_rect.left<pos[0]<gameover_rect.right and \ gameover_rect.top<pos[1]<gameover_rect.bottom: pygame.quit() sys.exit() #绘制暂停按钮 if life_num != 0: screen.blit(paused_image, paused_rect) #切换图片 if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) clock = pygame.time.Clock() # 中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 me = myplane.MyPlane(bg_size) enemies = pygame.sprite.Group() # 生成敌方小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 5) big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 1) running = True switch_image = True delay = 100 score = 0 score_font = pygame.font.Font("font/font.ttf", 36) bullets = [] # 生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 5 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # 生命数量 life_image = pygame.image.load("images/life.png").convert_alpha() life_rect = life_image.get_rect() life_num = 10 # 游戏结束画面 gameover_font = pygame.font.Font("font/font.ttf", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() DOUBLE_BULLET_TIME = USEREVENT + 1 # 解除我方飞机无敌状态 INVINCEBLE_TIME = USEREVENT + 2 # 生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) # 标记是否使用超级子弹 is_double_bullet = False level = 1 # 全屏炸弹 bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 # 每30秒发放一个补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) # 阻止重复读取成绩记录文件 recorded = False # 标志是否暂停游戏 paused = False paused_nor_image = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load("images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load("images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load("images/resume_pressed.png").convert_alpha() paused_rect = paused_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = paused_nor_image while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() paused_image = resume_pressed_image else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() paused_image = pause_pressed_image elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = paused_nor_image elif event.type == KEYDOWN: if event.key == K_ < em class ="Highlight" style="padding: 1px; box-shadow: rgb(229, 229, 229) 1px 1px; border-radius: 3px; -webkit-print-color-adjust: exact; background-color: rgb(255, 255, 102); color: rgb(0, 0, 0); font-style: inherit;" > SPA < / em > CE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if random.choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0)
def main(): #pygame.mixer.music.play(n,start,stop) #第一个参数为播放次数,如果是-1表示循环播放,省略表示只播放1次。第二个参数和第三个参数分别表示播放的起始和结束位置。 pygame.mixer.music.play(-1) clock = pygame.time.Clock() #生成我方飞机 me = myplane.MyPlane(bg_size) #生成敌方飞机 enemies = pygame.sprite.Group() #生成敌方小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) #中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 #统计得分 score = 0 score_font = pygame.font.Font(None, 36) life_image = pygame.image.load("images/me2.png").convert_alpha() life_rect = life_image.get_rect() life_num = 3 #标志是否暂停游戏 paused = False pause_nor_image = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load("images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load("images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load("images/resume_pressed.png").convert_alpha() paused_rect = resume_nor_image.get_rect() paused_rect.left, paused_rect.top = width-paused_rect.width-10, 10 paused_image = resume_nor_image #生成普通子弹 bullet1 = [] bullet1_index = 0 bullet1_num = 4 for i in range(bullet1_num): bullet1.append(bullet.Bullet1(me.rect.midtop)) #生产超级子弹 bullet2 = [] bullet2_index = 0 bullet2_num = 8 for i in range(bullet2_num): bullet2.append(bullet.Bullet2((me.rect.centerx-20, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx+20, me.rect.centery))) running = True #用于延迟 delay = 100 #设置难度等级 level = 1 bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font(None, 48) bomb_num = 3 #每30s发放一个补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) #用户自定义事件 SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30*1000) #超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 #标志是否使用超级子弹 is_double_bullet = False #解除我方无敌 状态定时器 INVINCIBLE_TIME = USEREVENT + 2 while running: for event in pygame.event.get(): if event.type == QUIT: #如果用IDLE打开的话,直接关闭窗口的话 无法关闭,加上这个能关闭窗口 pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: #发放包设置为0,取消这个事件 pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause()#背景音乐暂停 pygame.mixer.pause()#暂停音效 else: pygame.time.set_timer(SUPPLY_TIME, 30*1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: pass else: paused_image = pause_nor_image else: if paused: pass else: paused_image = resume_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) screen.blit(background, (0, 0)) if level == 1 and score > 5000: level = 2 add_big_enemies(big_enemies, enemies, 1) add_mid_enemies(mid_enemies, enemies, 2) add_small_enemies(small_enemies, enemies, 3) inc_speed(small_enemies, 1) if level == 2 and score > 6000000: level = 3 add_big_enemies(big_enemies, enemies, 1) add_mid_enemies(mid_enemies, enemies, 3) add_small_enemies(small_enemies, enemies, 5) inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) if level == 3 and score > 9000000: level = 4 add_big_enemies(big_enemies, enemies, 1) add_mid_enemies(mid_enemies, enemies, 3) add_small_enemies(small_enemies, enemies, 5) inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) if level == 4 and score > 10000000: level = 5 add_big_enemies(big_enemies, enemies, 1) add_mid_enemies(mid_enemies, enemies, 3) add_small_enemies(small_enemies, enemies, 5) inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) if life_num and not paused: #检测用户的键盘操作 key_pressed包含所有键盘的布尔值 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() #绘制全屏炸弹补给并检测 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(me, bomb_supply): if bomb_num < 3: bomb_num += 1 bomb_supply.active = False if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(me, bullet_supply): is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18*1000) bullet_supply.active = False #发射子弹 if not(delay % 10): if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset((me.rect.centerx-20, me.rect.centery)) bullets[bullet2_index].reset((me.rect.centerx+20, me.rect.centery)) bullet2_index = (bullet2_index+1)%bullet2_num else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % bullet1_num #检测子弹是否击中敌机 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide(b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False #绘制大型机 for each in big_enemies: if each.active: each.move() screen.blit(each.image, each.rect) #绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top-5), (each.rect.right, each.rect.top-5), 2) energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, (each.rect.left, each.rect.top-5), (each.rect.left+each.rect.width*energy_remain, each.rect.top-5), 2) #即将出现在画面中,播放音效 if each.rect.bottom > -50 and each.rect.bottom < each.height // 2: enemy3_down_sound.play(-1) #毁灭 else: screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 1 if e3_destroy_index == 0: score += 10000 each.reset() #绘制中型机 for each in mid_enemies: if each.active: each.move() screen.blit(each.image, each.rect) #绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top-5), (each.rect.right, each.rect.top-5), 2) energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, (each.rect.left, each.rect.top-5), (each.rect.left+each.rect.width*energy_remain, each.rect.top-5), 2) #毁灭 else: screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 1 if e2_destroy_index == 0: score += 6000 each.reset() #绘制小型机 for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) #毁灭 else: screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 1 if e1_destroy_index == 0: score += 1000 each.reset() #检查我方飞机是否被碰撞, 这个函数的第一个参数就是单个精灵,第二个参数是精灵组,第三个参数是一个bool值,当为True的时候,会删除组中所有冲突的精灵,False的时候不会删除冲突的精灵 enemies_down = pygame.sprite.spritecollide(me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False #绘制我方飞机 if me.active: screen.blit(me.image, (me.rect.left, me.rect.top)) #毁灭 else: screen.blit(each.destroy_images[me_destroy_index], each.rect) me_destroy_index = (me_destroy_index + 1) % 1 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3*1000) #绘制剩余生命的数量 if life_num: for i in range(life_num): screen.blit(life_image, (width-10-(i+1)*life_rect.width, height-10-life_rect.height)) score_text = score_font.render("Score: %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) screen.blit(paused_image, paused_rect) #绘制全屏炸弹 bomb_text = bomb_font.render("x %d" % bomb_num, True, WHITE) text_bomb = rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height-10-bomb_rect.width)) screen.blit(bomb_text, (20+bomb_rect.width, height-5-text_bomb.height)) if not delay: delay = 100 delay = delay - 1 pygame.display.flip() #一秒钟页面刷新60次,即60帧,即一次while循环是1帧 clock.tick(60) elif life_num == 0: print("GAME OVER!") running = False
def main(): # ----------------------------------- # 背景音乐持续播放 pygame.mixer.music.play(-1) # 生成我方飞机 me = heroplane.HeroPlane(bg_size) enemies = pygame.sprite.Group() # 生成敌方小型飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 10) # 生成敌方中型飞机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 3) # 生成敌方大型飞机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) # 生成敌方特殊飞机 plus_enemies = enemy.PlusEnemy(bg_size) # 生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # 生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) bullet3 = [] bullet3_index = 0 BULLET3_NUM = 21 for i in range(BULLET3_NUM // 2): bullet3.append(bullet.Bullet2((me.rect.centerx - 30, me.rect.centery))) bullet3.append(bullet.Bullet2((me.rect.centerx - 00, me.rect.centery))) bullet3.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) # 生成敌方 子弹 bullet4 = [] bullet4_index = 0 BULLET4_NUM = 20 for i in range(BULLET4_NUM): bullet4.append(bullet.Bullet_enemy(plus_enemies.rect.midbottom)) clock = pygame.time.Clock() # 中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 e4_destroy_index = 0 me_destroy_index = 0 # 统计得分 score = 0 score_font = pygame.font.Font("font/font.ttf", 36) # 标志是否暂停游戏 paused = False pause_nor_image = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load( "images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load( "images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load( "images/resume_pressed.png").convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image # 标志开始游戏 # start_flag = False # start_flag_pressed_image = pygame.image.load( # "images/resume_nor.png").convert_alpha() # start_rect = start_flag_pressed_image.get_rect() # 设置难度级别 level = 1 Level_MAX_Flag = False # 全屏炸弹 bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 1000 MAX_BOMB_NUM = 1000 # 初始每30秒发放一个补给包 # 随着关卡难度上升补给时间间隔缩短 # 基本单位设置为毫秒级别,不建议把时间设置的太低 Invincible_supply = supply.Invincible_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) supply_Inset_time = 30 SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, supply_Inset_time * 1000) # 超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 # 标志是否使用超级子弹 is_double_bullet = False is_thirh_bullet = False # 复活的无敌状态 # 解除我方无敌状态定时器 INVINCIBLE_TIME = USEREVENT + 2 # 生命数量 life_image = pygame.image.load("images/life.png").convert_alpha() life_rect = life_image.get_rect() life_num = 3 MAX_LIFE_NUM = 3 # 用于阻止重复打开记录文件 recorded = False # 游戏结束画面 gameover_flag = False gameover_font = pygame.font.Font("font/font.TTF", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() # 用于切换图片 switch_image = True # 游戏进行时间计时 Time_Running_Count = time.time() # 用于延迟 delay = 100 running = True """ Game Start """ while running: y1, y2 = bg_update() # pygame.event.get() 从队列中获取事件 for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: # 暂停状态 pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False # b键 自爆清屏 elif event.key == K_b: me.active = False if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: # 毁灭 if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False # Q键 暂停 elif event.key == K_q: if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.key == K_1: life_num = 0 elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bomb_supply.reset() else: Invincible_supply.reset() # Invincible_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) # 根据用户的得分增加难度 # 选加项: 难度增加,生命值增加 if level == 1 and score < 50000 and score >= 10000: level = 2 upgrade_sound.play() # 增加3架小型敌机、2架中型敌机和1架大型敌机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) # 提升小型敌机的速度 inc_speed(small_enemies, 1) life_num = gmplus.Life_plus(life_num, MAX_LIFE_NUM) supply_Inset_time -= 3 elif level == 2 and score < 100000 and score >= 50000: level = 3 upgrade_sound.play() # 增加5架小型敌机、3架中型敌机和2架大型敌机 add_small_enemies(small_enemies, enemies, 4) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) # 提升小型敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) life_num = gmplus.Life_plus(life_num, MAX_LIFE_NUM) supply_Inset_time -= 3 elif level == 3 and score < 200000 and score >= 100000: level = 4 upgrade_sound.play() # 提升小型敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) life_num = gmplus.Life_plus(life_num, MAX_LIFE_NUM) supply_Inset_time -= 3 elif level == 4 and (not Level_MAX_Flag) and score > 200000: level = 5 Level_MAX_Flag = True upgrade_sound.play() # 提升小型敌机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) life_num = gmplus.Life_plus(life_num, MAX_LIFE_NUM) supply_Inset_time -= 3 # screen.blit(background, (0, 0)) if life_num and not paused: # 检测用户的键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() # 绘制全屏炸弹补给并检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < MAX_BOMB_NUM: bomb_num += 2 if bomb_num > MAX_BOMB_NUM: bomb_num = MAX_BOMB_NUM bomb_supply.active = False # 无敌状态补给检测 # 绘制无敌补给并检测是否获得 if Invincible_supply.active: Invincible_supply.move() screen.blit(Invincible_supply.image, Invincible_supply.rect) if pygame.sprite.collide_mask(Invincible_supply, me): get_bullet_sound.play() # is_double_bullet = True me.invincible = True pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) Invincible_supply.active = False # 我方发射子弹 # 发射子弹的类型变更判断 if level < 5 and level >= 3: is_double_bullet = True elif level >= 5: is_double_bullet = False is_thirh_bullet = True # 发射子弹 if not (delay % 10): bullet_sound.play() if is_thirh_bullet: bullets = bullet3 bullets[bullet3_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet3_index + 1].reset( (me.rect.centerx - 00, me.rect.centery)) bullets[bullet3_index + 2].reset( (me.rect.centerx + 30, me.rect.centery)) bullet3_index = (bullet3_index + 3) % BULLET3_NUM elif is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM # 检测子弹是否击中敌机 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) enemy_bullets_hit = pygame.sprite.collide_rect( b, plus_enemies) if enemy_bullets_hit: b.active = False plus_enemies.active = False if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False # 敌方发射子弹 if not (delay % 100): bullet_sound.play() bullets_enemy = bullet4 bullets_enemy[bullet4_index].reset(plus_enemies.rect.midbottom) bullet4_index = (bullet4_index + 1) % BULLET4_NUM print("敌方子弹发射了") # 绘制大型敌机 for each in big_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) # 当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line( screen, energy_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) # 即将出现在画面中,播放音效 if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: # 毁灭 if not (delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 each.reset() # 绘制中型敌机: for each in mid_enemies: if each.active: each.move() if delay > 50: each.moveRight() else: each.moveLeft() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) # 当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line( screen, energy_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * energy_remain, each.rect.top - 5), 2) else: # 毁灭 if not (delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 each.reset() # 绘制小型敌机: for each in small_enemies: if each.active: each.move() if delay > 50: each.moveLeft() else: each.moveRight() screen.blit(each.image, each.rect) else: # 毁灭 if not (delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() # 绘制特殊敌机: if plus_enemies.active: plus_enemies.move() screen.blit(plus_enemies.image, plus_enemies.rect) else: # 毁灭 print("消灭了") if not (delay % 3): if e4_destroy_index == 0: enemy1_down_sound.play() screen.blit(plus_enemies.destroy_images[e4_destroy_index], plus_enemies.rect) e4_destroy_index = (e4_destroy_index + 1) % 4 if e4_destroy_index == 0: print("加分了") score += 3000 plus_enemies.reset() # 检测敌军子弹是否击中友军飞机 for b in bullets_enemy: if b.active: b.move() screen.blit(b.image, b.rect) enemy_bullets_hit = pygame.sprite.collide_rect(b, me) if enemy_bullets_hit and not me.invincible: me.active = False b.active = False # 敌机间的碰撞检测 for each_a in enemies: for each_b in enemies: if each_a != each_b: enemies_Collide = pygame.sprite.collide_rect( each_a, each_b) if enemies_Collide: if each_a.rect.left < each_b.rect.left: each_a.rect.left -= 10 each_b.rect.left += 10 else: each_a.rect.left += 10 each_b.rect.left -= 10 # 检测我方飞机是否被撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) enemies_plus_enemies = pygame.sprite.collide_rect(me, plus_enemies) if enemies_plus_enemies and not me.invincible: me.active = False plus_enemies.active = False if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False # 绘制我方飞机 if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: # 毁灭 if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) # 绘制全屏炸弹数量 bomb_text = bomb_font.render("× %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # 绘制剩余生命数量 if life_num: for i in range(life_num): screen.blit(life_image, (width - 10 - (i + 1) * life_rect.width, height - 10 - life_rect.height)) # 绘制得分 score_text = score_font.render("Score : %s" % str(score), True, WHITE) level_text = score_font.render("level : %s" % str(level), True, WHITE) small_size_text = score_font.render( "Small_Size : %s" % str(len(small_enemies)), True, WHITE) mid_size_text = score_font.render( "Mid_Size : %s" % str(len(mid_enemies)), True, WHITE) big_size_text = score_font.render( "Big_Size : %s" % str(len(big_enemies)), True, WHITE) screen.blit(score_text, (10, 5)) screen.blit(level_text, (10, 45)) screen.blit(small_size_text, (10, 85)) screen.blit(mid_size_text, (10, 125)) screen.blit(big_size_text, (10, 165)) # 绘制游戏结束画面 elif life_num == 0: # Time_Ending_Count = time.time() # 部分变量初始化 level = 1 supply_Inset_time = 30 gameover_flag = True # 背景音乐停止 pygame.mixer.music.stop() # 停止全部音效 pygame.mixer.stop() # 停止发放补给 pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True # 读取历史最高得分 with open("record.txt", "r") as f: record_score = int(f.read()) # 如果玩家得分高于历史最高得分,则存档 if score > record_score: with open("record.txt", "w") as f: f.write(str(score)) # 绘制结束画面 record_score_text = score_font.render( "Best : %d" % max(record_score, score), True, (255, 255, 255)) screen.blit(record_score_text, (50, 50)) gameover_text1 = gameover_font.render("Your Score", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = \ (width - again_rect.width) // 2, \ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) # 检测用户的鼠标操作 # 如果用户按下鼠标左键 if pygame.mouse.get_pressed()[0]: # 获取鼠标坐标 pos = pygame.mouse.get_pos() # 如果用户点击“重新开始” if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: # 调用main函数,重新开始游戏 # gameover_flag = False main() # 如果用户点击“结束游戏” elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: # 退出游戏 pygame.quit() sys.exit() # 绘制暂停按钮 if (not gameover_flag): screen.blit(paused_image, paused_rect) # 切换图片 if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) #initialize gamer's plane me = myplane.MyPlane(bg_size) #initialize enemy planes enemies = pygame.sprite.Group() #initialize small enemies small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) #initialize mid enemies mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) #initialize large enemies large_enemies = pygame.sprite.Group() add_large_enemies(large_enemies, enemies, 2) clock = pygame.time.Clock() #generate normal bullet bullet1 = [] bullet1_index = 0 BULLET1_NUM = 5 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) #generate super bullet bullet_speed = 10 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 16 for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) # gamer's score score = 0 score_font = pygame.font.Font("font/font.ttf", 36) e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 # pasue and resume paused = False pause_nor_image = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load( "images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load( "images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load( "images/resume_pressed.png").convert_alpha() pause_rect = pause_nor_image.get_rect() pause_rect.left, pause_rect.top = width - pause_rect.width - 10, 10 paused_image = pause_nor_image # level level = 1 # bomb bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font("font/font.ttf", 48) bomb_num = 3 # supply every 30 seconds bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) # super bullet timer DOUBLE_BULLET_TIME = USEREVENT + 1 is_double_bullet = False # hack mode timer HACKER_TIME = USEREVENT + 2 # life remain life_image = pygame.image.load("images/life.png").convert_alpha() life_rect = life_image.get_rect() life_num = 3 #for plane image switch switch_image = True # prevent repeating open files recorded = False # gameover images gameover_font = pygame.font.Font("font/font.ttf", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() #delay delay = 100 running = True while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and pause_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if pause_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bullet_supply.reset() else: bomb_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == HACKER_TIME: me.hack_mode = False pygame.time.set_timer(HACKER_TIME, 0) # increase difficulty if level == 1 and score > 100000: level = 2 upgrade_sound.play() # +3 small enemies, +2 mid enemies, +1 large enemy add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_large_enemies(large_enemies, enemies, 1) # increase small enemies's speed increase_speed(small_enemies, 1) elif level == 2 and score > 200000: level = 3 upgrade_sound.play() # +5 small enemies, +3 mid enemies, +1 large enemy add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_large_enemies(large_enemies, enemies, 1) # increase small and mid enemies's speed increase_speed(small_enemies, 1) increase_speed(mid_enemies, 1) elif level == 3 and score > 300000: level = 4 upgrade_sound.play() # +5 small enemies, +3 mid enemies, +1 large enemy add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_large_enemies(large_enemies, enemies, 2) # increase small and mid enemies's speed increase_speed(small_enemies, 1) increase_speed(mid_enemies, 1) elif level == 4 and score > 500000: level = 5 upgrade_sound.play() # +5 small enemies, +3 mid enemies, +1 large enemy add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_large_enemies(large_enemies, enemies, 2) # increase small and mid enemies's speed increase_speed(small_enemies, 1) increase_speed(mid_enemies, 1) screen.blit(background, (0, 0)) if life_num and not paused: #key press key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() # collision with supply if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() bomb_num += 1 bomb_supply.active = False if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False # shoot bullet if not (delay % bullet_speed): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM bullet_speed = 5 else: bullets = bullet1 bullet1[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM bullet_speed = 10 #decet bullet collision for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in large_enemies: e.hit = True e.hp -= 1 if e.hp == 0: e.active = False else: e.active = False # large enemies on screen for each in large_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) # hp bar pygame.draw.line(screen, WHITE, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) # display green if hp > 20%, else display red hp_remain = each.hp / enemy.LargeEnemy.hp if hp_remain > 0.2: hp_color = GREEN else: hp_color = RED pygame.draw.line( screen, hp_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * hp_remain, each.rect.top - 5), 2) # generate sound effect for large enemies if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: #destroy if not (delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 each.reset() # mid enemies on screen for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # hp bar pygame.draw.line(screen, WHITE, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) # display green if hp > 20%, else display red hp_remain = each.hp / enemy.MidEnemy.hp if hp_remain > 0.2: hp_color = GREEN else: hp_color = RED pygame.draw.line( screen, hp_color, (each.rect.left, each.rect.top - 5), (each.rect.left + each.rect.width * hp_remain, each.rect.top - 5), 2) else: #destroy if not (delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 each.reset() # small enemies on screen for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: #destroy if not (delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 each.reset() # showing gamer's plane on screen if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: #destroy if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], each.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() # set hack time pygame.time.set_timer(HACKER_TIME, 3 * 1000) # bomb number icon on screen bomb_text = bomb_font.render("× %d" % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # life remain icon on screen if life_num: for i in range(life_num): screen.blit(life_image, (width - 10 - (i + 1) * life_rect.width, height - 10 - life_rect.height)) #score on screen score_text = score_font.render("Score : %s" % str(score), True, WHITE) screen.blit(score_text, (10, 5)) #pause icon on screen screen.blit(paused_image, pause_rect) #detect gamer's plane collision enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.hack_mode: me.active = False #!!!!!!!!!!!!!!!!!!!!! for e in enemies_down: e.active = False # game over screen elif life_num == 0: # stop bg music pygame.mixer.music.stop() # stop mixers pygame.mixer.stop() # stop supply pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True # read highest score with open("record.txt", "r") as f: record_score = int(f.read()) # save hishest score if score > record_score: with open("record.txt", "w") as f: f.write(str(score)) if record_score > score: higher_score = record_score else: higher_score = score # game end interface record_score_text = score_font.render("Best : %d" % higher_score, True, (255, 255, 255)) screen.blit(record_score_text, (50, 50)) gameover_text1 = gameover_font.render("Your Score", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = ( width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = ( width - gameover_text2_rect.width ) // 2, gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = ( width - again_rect.width) // 2, gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = ( width - again_rect.width) // 2, again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) if pygame.mouse.get_pressed()[0]: pos = pygame.mouse.get_pos() if again_rect.left < pos[ 0] < again_rect.right and again_rect.top < pos[ 1] < again_rect.bottom: main() elif gameover_rect.left < pos[ 0] < gameover_rect.right and gameover_rect.top < pos[ 1] < gameover_rect.bottom: pygame.quit() sys.exit() #pic switch if not (delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) #生成我方飞机 me = myplane.MyPlane(bg_size) # 生成敌方飞机 enemies = pygame.sprite.Group() # 生成大飞机 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, enemy3_num) # 生成中飞机 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, enemy2_num) # 生成小飞机 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, enemy1_num) # 生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # 生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) # 用户切换图片 switch = True # 用于延迟 delay = 100 clock = pygame.time.Clock() e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 # 统计得分 score = 0 score_font = pygame.font.Font('font/font.ttf', 36) # 是否暂停游戏 paused = False pause_nor_image = pygame.image.load('images/pause_nor.png').convert_alpha() pause_pressed_image = pygame.image.load( 'images/pause_pressed.png').convert_alpha() resume_nor_image = pygame.image.load( 'images/resume_nor.png').convert_alpha() resume_pressed_image = pygame.image.load( 'images/resume_pressed.png').convert_alpha() pause_rect = pause_nor_image.get_rect() pause_rect.left, pause_rect.top = width - pause_rect.width - 10, 10 pause_image = pause_nor_image # 难度级别 level = 1 # 炸弹 bomb_image = pygame.image.load('images/bomb.png').convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.Font('font/font.ttf', 40) bomb_num = 3 # 每30秒发放一个补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) # 超级子弹定时器 DOUBLE_BULLET_TIME = USEREVENT + 1 # 是否使用超级子弹 is_double_bullet = False # 生命数量 life_image = pygame.image.load('images/life.png').convert_alpha() life_rect = life_image.get_rect() life_num = 3 # 无敌时间计时器 INVINCIBLE_TIME = USEREVENT + 2 # 防止重复打开记录文件 recorded = False running = True # 是否播放大飞机fly的音效 play_fly_sound = False while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() # 暂停 elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and pause_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if pause_rect.collidepoint(event.pos): if paused: pause_image = resume_pressed_image else: pause_image = pause_pressed_image else: if paused: pause_image = resume_nor_image else: pause_image = pause_nor_image elif event.type == KEYDOWN: # 非停止状态下按下空格才释放炸弹 if not paused and event.key == K_SPACE: if bomb_num > 0: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): bomb_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) # 根据得分增加难度 # 可根据自己喜好修改 if level == 1 and score > 50: level = 2 update_sound.play() # 增加 add_small_enemies(small_enemies, enemies, 2) add_mid_enemies(mid_enemies, enemies, 1) add_big_enemies(big_enemies, enemies, 1) elif level == 2 and score > 200: level = 3 update_sound.play() # 增加 add_small_enemies(small_enemies, enemies, 2) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 0) #提升速度 increase_speed(small_enemies, 1) elif level == 3 and score > 500: level = 4 update_sound.play() # 增加 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) #提升速度 increase_speed(mid_enemies, 1) elif level == 4 and score > 1200: level = 5 update_sound.play() # 增加 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 1) add_big_enemies(big_enemies, enemies, 1) #提升速度 increase_speed(small_enemies, 1) increase_speed(mid_enemies, 1) screen.blit(background, (0, 0)) if life_num and not paused: # 检测用户的键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() # 绘制全屏炸弹补给并检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False # 绘制超级子弹补给并检测是否获得 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() # 发射超级子弹 is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False # 发射子弹 if not (delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM #检测子弹是否击中敌机 for b in bullets: enemies_hit = [] if b.active: b.move() screen.blit(b.image, b.rect) enemies_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemies_hit: b.active = False for e in enemies_hit: e.hit = True if e in mid_enemies or e in big_enemies: e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False # 绘制大飞机 # 一开始先认为不需要播放大飞机飞行的音效 play_fly_sound = False for each in big_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) #绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5),\ (each.rect.right, each.rect.top - 5),\ 2) #当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5),\ (each.rect.left + each.rect.width * energy_remain,\ each.rect.top - 5), 2) # 即将出现在画面中播放音效 # 只要有一个大飞机处于这个范围内,就播放大飞机飞行音效 if each.rect.bottom > -50 and each.rect.top < bg_size[1]: play_fly_sound = True else: # 毁灭 if not (delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: score += 10 each.reset() # 决定是否播放大飞机飞行音效 if play_fly_sound: enemy3_fly_sound.play(-1) play_fly_sound = False else: enemy3_fly_sound.stop() #绘制中飞机 for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) #绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5),\ (each.rect.right, each.rect.top - 5),\ 2) #当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5),\ (each.rect.left + each.rect.width * energy_remain,\ each.rect.top - 5), 2) else: # 毁灭 if not (delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6 each.reset() #绘制小飞机 for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: # 毁灭 if not (delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1 each.reset() # 检测我方飞机是否被撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False # 绘制我方飞机 if me.active: if switch: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: # 毁灭 if not (delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) # 绘制炸弹 bomb_text = bomb_font.render('x %d' % bomb_num, True, WHITE) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # 绘制生命数量 if life_num: for i in range(life_num): screen.blit(life_image,\ (width - (i + 1) * life_rect.width - 10, \ height - life_rect.height - 10)) # 绘制得分 score_text = score_font.render('Score : %s' % str(score), True, WHITE) screen.blit(score_text, (10, 5)) # 绘制游戏结束画面 elif life_num == 0: # 停止背景音乐 pygame.mixer.music.stop() # 停止音效 pygame.mixer.stop() # 停止补给 pygame.time.set_timer(SUPPLY_TIME, 0) #读取历史最高分 if not recorded: recorded = True with open('record.txt', 'r') as f: record_score = int(f.read()) if score > record_score: with open('record.txt', 'w') as f: f.write(str(score)) # 绘制结束界面 score_font = pygame.font.Font('font/font.ttf', 40) gameover_font = pygame.font.Font('font/font.ttf', 40) again_image = pygame.image.load('images/again.png').convert_alpha() gameover_image = pygame.image.load( 'images/gameover.png').convert_alpha() record_score_text = score_font.render('Best : %d' % record_score, True, WHITE) screen.blit(record_score_text, (10, 10)) gameover_text1 = gameover_font.render('Your Score', True, WHITE) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 2 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, WHITE) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect = again_image.get_rect() again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect = gameover_image.get_rect() gameover_rect.left, gameover_rect.top = \ (width - gameover_rect.width) // 2, \ again_rect.bottom + 50 screen.blit(gameover_image, gameover_rect) # 检测用户操作,重新开始或者结束游戏 # 检测是否按下左键 if pygame.mouse.get_pressed()[0]: # 表示按下左键 # 获取鼠标坐标 pos = pygame.mouse.get_pos() if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: main() elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: pygame.quit() sys.exit() screen.blit(pause_image, pause_rect) if not delay % 5: switch = not switch delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): pygame.mixer.music.play(-1) # -1代表音乐循环播放 #生成我方飞机的实例化对象 me = myplane.MyPlane(bg_size) #引用别的文件的类,要把文件名打在类名前面 #生成敌方飞机的实例化对象 enemies = pygame.sprite.Group() #建一个Group来装入所有类型的敌机,用于进行碰撞检测 #生成小型飞机 small_enemies = pygame.sprite.Group() #建一个Group来装小型飞机,用于处理小型飞机的变化 add_small_enemies(small_enemies, enemies, 15) #调用方法,用来把飞机添加到Group中 #生成中型飞机 mid_enemies = pygame.sprite.Group() #建一个Group来装小型飞机,用于处理小型飞机的变化 add_mid_enemies(mid_enemies, enemies, 4) #调用方法,用来把飞机添加到Group中 #生成大型飞机 big_enemies = pygame.sprite.Group() #建一个Group来装小型飞机,用于处理小型飞机的变化 add_big_enemies(big_enemies, enemies, 2) #调用方法,用来把飞机添加到Group中 #生成特殊飞机group special_enemies = pygame.sprite.Group() #建一个Group来装特殊飞机,用于处理特殊飞机的变化 #初始化特殊飞机数目为5 special_enemies_num = 5 #生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) #初始化超级子弹 bullet2 = [] bullet2_index = 0 #超级子弹等级和字体 bullet2_level = 0 bullet_font = pygame.font.Font("font/font.ttf", 20) #生成终极子弹 bullet3 = [] bullet3_index = 0 BULLET3_NUM = 20 for i in range(BULLET3_NUM // 5): bullet3.append(bullet.Bullet1((me.rect.centerx - 58, me.rect.centery))) bullet3.append(bullet.Bullet1((me.rect.centerx + 55, me.rect.centery))) bullet3.append( bullet.Bullet1((me.rect.centerx - 27, me.rect.centery - 21))) bullet3.append( bullet.Bullet1((me.rect.centerx + 24, me.rect.centery - 21))) bullet3.append(bullet.Bullet1(me.rect.midtop)) #中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 e4_destroy_index = 0 me_destroy_index = 0 #用于我方飞机切换图片的判断变量 switch_image = True #用于延时的变量 delay = 100 #分数初始化 score = 0 #载入分数字体 score_font = pygame.font.Font("font/font.ttf", 30) #游戏难度初始化 level = 1 #一开始小型机,中型机 不会斜向飞行 small_direction_change = False mid_direction_change = False #炸弹初始化 bomb_num = 3 bomb_image = pygame.image.load("Images/shoot/bomb.png").convert_alpha() bomb_font = pygame.font.Font("font/font.ttf", 40) bomb_rect = bomb_image.get_rect() #游戏暂停按钮 paused = False paused_nor_image = pygame.image.load( "Images/shoot/game_pause_nor.png").convert_alpha() paused_pressed_image = pygame.image.load( "Images/shoot/game_pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load( "Images/shoot/game_resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load( "Images/shoot/game_resume_pressed.png").convert_alpha() paused_rect = paused_nor_image.get_rect() #获取图片矩形位置 paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = paused_nor_image #pause按钮的默认初始状态 #游戏道具的发放 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) #设定道具发定时器(自定义事件) SUPPLY_TIME = USEREVENT #定义一个自定义事件 名叫 SUPPLY_TIME pygame.time.set_timer(SUPPLY_TIME, 10 * 1000) #每10秒产生一次自定义事件SUPPLY_TIME #超级子弹定时器(自定义事件) DOUBLE_BULLET_TIME_FINISH = USEREVENT + 1 #定义一个自定义事件 名叫 DOUBLE_BULLET_TIME_FINISH 用来限制超级子弹使用的事件 #标志是否正在使用超级子弹 is_double_bullet = False #解除我方飞机无敌状态定时器(自定义事件) INVINCIBLE_TIME_FINISH = USEREVENT + 2 #自定义事件:用于暂停飞机无敌 #突发特殊小飞机定时器(自定义事件) SPECIAL_TIME = USEREVENT + 3 pygame.time.set_timer(SPECIAL_TIME, randint(20, 60) * 1000) #每20-60秒触发一次 #我方飞机生命数量 life_image = pygame.image.load("Images/shoot/life.png").convert_alpha() life_image_rect = life_image.get_rect() life_num_font = pygame.font.Font("font/font.ttf", 40) life_num = 3 #用于阻止重复打开记录文件 recorded = False #游戏结束画面,字体 record_score_font = pygame.font.Font("font/font.ttf", 35) finial_score_font = pygame.font.Font("font/font.ttf", 40) gameover_font = pygame.font.Font("font/font.ttf", 25) again_image = pygame.image.load( "Images/shoot/kuangkuang.png").convert_alpha() again_image_rect = again_image.get_rect() close_image = pygame.image.load( "Images/shoot/kuangkuang.png").convert_alpha() close_image_rect = close_image.get_rect() #用于延时主循环,控制游戏帧数,保护cpu clock = pygame.time.Clock() #游戏主循环 running = True while running: for event in pygame.event.get(): #检测事件循环 #触发退出事件 if event.type == pygame.QUIT: pygame.quit() sys.exit() #触发鼠标移动事件 elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint( event.pos): #第二个条件的意思:当鼠标移动到paused_rect位置时返回True paused = not paused if paused: #如果按了暂停,所有声音暂停,补给事件 暂停产生 pygame.time.set_timer(SUPPLY_TIME, 0) #如果暂停,“补给事件”自定义事件 暂停产生 pygame.mixer.music.pause() #背景音乐暂停 pygame.mixer.pause() #音效暂停 else: #如果不是暂停,所有声音正常播放,补给事件正常产生 pygame.time.set_timer(SUPPLY_TIME, 30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint( event.pos): #判断鼠标的位置是否在paused_rect这个位置上,如果是就显示“深 色”图标 if paused: paused_image = resume_pressed_image #如果在暂停的情况下,图片变成“深 色 继 续”图片 else: paused_image = paused_pressed_image #如果在继续的情况下,图片变成“深 色 暂 停”图片 else: #如果鼠标没在paused_rect上方的话,就显示 “浅 色” 图标 if paused: paused_image = resume_nor_image else: paused_image = paused_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False #触发道具补给事件 elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True, False]): #在True 和 False 中 随机选一个 bomb_supply.reset() else: bullet_supply.reset() #触发超级子弹结束 elif event.type == DOUBLE_BULLET_TIME_FINISH: is_double_bullet = False #超级子弹效果取消 pygame.time.set_timer(DOUBLE_BULLET_TIME_FINISH, 0) #暂停自定义事件的产生 #触发解除飞机无敌事件 elif event.type == INVINCIBLE_TIME_FINISH: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME_FINISH, 0) #触发特殊飞机事件 elif event.type == SPECIAL_TIME: enemy.SpecialEnemy.happen = True #生成特殊飞机 add_special_enemies(special_enemies, enemies, special_enemies_num) #调用方法,用来把飞机添加到Group中 #游戏难度 if level == 1 and score > 50000: level = 2 upgrade_sound.play() #增加3架小型机,2架中型机,1架大型机 add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) #提升小型机的速度 inc_speed(small_enemies, 1) elif level == 2 and score > 100000: level = 3 upgrade_sound.play() #增加5架小型机,3架中型机,2架大型机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升小型机和中型机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) #小型飞机开始斜向飞行 small_direction_change = True #特殊小飞机数目+1 special_enemies_num += 1 elif level == 3 and score > 200000: level = 4 upgrade_sound.play() #增加5架小型机,3架中型机,2架大型机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升小型机、中型机、大型机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) life_num += 1 #特殊小飞机数目+2 special_enemies_num += 2 elif level == 4 and score > 450000: level = 5 upgrade_sound.play() #增加5架小型机,3架中型机,2架大型机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升小型机和中型机的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) #中型机飞行方向改变 mid_direction_change = True life_num += 1 #特殊小飞机数目+2 special_enemies_num += 2 elif level == 4 and score > 800000: level = 5 upgrade_sound.play() #增加5架小型机,3架中型机,2架大型机 add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) #提升小型机、中型机、大型的速度 inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) life_num += 1 #特殊小飞机数目+2 special_enemies_num += 2 elif level == 5 and score > 1000000: level = 6 upgrade_sound.play() inc_speed(small_enemies, 1) enemy.MidEnemy.energy = 13 enemy.BigEnemy.energy = 25 elif level == 6 and score > 1500000: level = 7 upgrade_sound.play() inc_speed(small_enemies, 2) inc_speed(mid_enemies, 1) enemy.MidEnemy.energy = 18 enemy.BigEnemy.energy = 35 elif level == 7 and score > 2000000: level = 8 upgrade_sound.play() inc_speed(small_enemies, 2) inc_speed(mid_enemies, 2) inc_speed(big_enemies, 1) enemy.MidEnemy.energy = 20 enemy.BigEnemy.energy = 40 #绘制背景图 screen.blit(background, (0, 0)) #当生命数大于0,还有没按下暂停时,游戏才继续进行 if life_num and not paused: #检测用户的键盘操作 key_press = pygame.key.get_pressed( ) #获取键盘上所有键的状态,返回一个bool值序列,表示键是否被按下 if key_press[K_w] or key_press[K_UP]: me.moveUp() if key_press[K_s] or key_press[K_DOWN]: me.moveDown() if key_press[K_a] or key_press[K_LEFT]: me.moveLeft() if key_press[K_d] or key_press[K_RIGHT]: me.moveRight() #绘制全屏炸弹补给,并检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) #绘制炸弹补给 if pygame.sprite.collide_mask( bomb_supply, me): #直接检测bomb_supply, me两个精灵是否发生碰撞 get_bomb_sound.play() if bomb_num < 5: #如果原本炸弹数<5个,就能获得一个炸弹 bomb_num += 1 bomb_supply.active = False #获得炸弹补给后,该补给图片消失 #绘制超级子弹补给,并检测是否获得 if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask( bullet_supply, me): #直接检测bomb_supply, me两个精灵是否发生碰撞 get_bullet_sound.play() bullet_supply.active = False bullet2_level += 1 #超级子弹等级+1 #如果超级子弹等级小于8,则发射超级子弹 if bullet2_level < 8: is_double_bullet = True #开始发射超级子弹 pygame.time.set_timer( DOUBLE_BULLET_TIME_FINISH, 18 * 1000 ) #自定义事件DOUBLE_BULLET_TIME_FINISH将在18秒后产生(18秒后,超级子弹失效) #生成超级子弹 if bullet2_level == 1: # 1级:每次发2颗 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append( bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append( bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) elif bullet2_level == 2: # 2级:每次发3颗 BULLET2_NUM = 12 for i in range(BULLET2_NUM // 3): bullet2.append( bullet.Bullet2((me.rect.centerx - 33, me.rect.centery))) bullet2.append( bullet.Bullet2((me.rect.centerx + 30, me.rect.centery))) bullet2.append(bullet.Bullet2(me.rect.midtop)) elif bullet2_level == 3: # 3级:每次发4颗 BULLET2_NUM = 16 for i in range(BULLET2_NUM // 4): bullet2.append( bullet.Bullet2((me.rect.centerx - 43, me.rect.centery))) bullet2.append( bullet.Bullet2((me.rect.centerx + 40, me.rect.centery))) bullet2.append( bullet.Bullet2((me.rect.centerx - 18, me.rect.centery))) bullet2.append( bullet.Bullet2((me.rect.centerx + 15, me.rect.centery))) elif 4 <= bullet2_level < 8: # 4级~7级:每次发5颗 BULLET2_NUM = 20 for i in range(BULLET2_NUM // 5): bullet2.append( bullet.Bullet2((me.rect.centerx - 58, me.rect.centery))) bullet2.append( bullet.Bullet2((me.rect.centerx + 55, me.rect.centery))) bullet2.append( bullet.Bullet2((me.rect.centerx - 27, me.rect.centery - 21))) bullet2.append( bullet.Bullet2((me.rect.centerx + 24, me.rect.centery - 21))) bullet2.append(bullet.Bullet2(me.rect.midtop)) #如果超级子弹等级已经到达8级,就不触发超级子弹了,而是触发终极子弹 if bullet2_level == 8: is_double_bullet = False #绘制大型飞机 for each in big_enemies: if each.active: #飞机移动 each.move() #绘制飞机 if each.hit: screen.blit(each.hit_image, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) #绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) #当生命值大于20%时,显示绿色血条,否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy #计算血量的百分比 if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line( screen, energy_color, (each.rect.left, each.rect.top - 5), (each.rect.left + energy_remain * each.rect.width, each.rect.top - 5), 2) #即将出现在画面中前,播放音效 if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: #飞机毁灭 if not (delay % 3): #每次当delay能整除3的时候,就显示一张图片 if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = ( e3_destroy_index + 1) % 6 #这里是一个小技巧,这样 e3_destroy_index的值只能是0~5 if e3_destroy_index == 0: #当飞机毁灭图片显示完时,就重置飞机 enemy3_fly_sound.stop() score += 10000 each.reset() #绘制中型飞机 for each in mid_enemies: if each.active: #飞机移动 if not mid_direction_change: each.direction -= each.direction #这样写能确保在direction_change激活前,保持中型机都垂直飞行的 each.move() if each.rect.right >= width: each.direction = -each.direction elif each.rect.left <= 0: each.direction = -each.direction screen.blit(each.image, each.rect) #绘制飞机 if each.hit: screen.blit(each.hit_image, each.rect) each.hit = False else: screen.blit(each.image, each.rect) #绘制血槽 pygame.draw.line(screen, BLACK, (each.rect.left, each.rect.top - 5), (each.rect.right, each.rect.top - 5), 2) #当生命值大于20%时,显示绿色血条,否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy #计算血量的百分比 if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line( screen, energy_color, (each.rect.left, each.rect.top - 5), (each.rect.left + energy_remain * each.rect.width, each.rect.top - 5), 2) else: #飞机毁灭 if not (delay % 3): #每次当delay能整除3的时候,就显示一张图片 if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = ( e2_destroy_index + 1) % 4 #这里是一个小技巧,这样 e2_destroy_index的值只能是0~3 if e2_destroy_index == 0: #当飞机毁灭图片显示完时,就重置飞机 score += 6000 each.reset() #绘制小型飞机 for each in small_enemies: if each.active: if not small_direction_change: each.direction -= each.direction #这样写能确保在direction_change激活前,保持小型机都垂直飞行的 each.move() if each.rect.right >= width: each.direction = -each.direction elif each.rect.left <= 0: each.direction = -each.direction screen.blit(each.image, each.rect) else: #飞机毁灭 if not (delay % 3): #每次当delay能整除3的时候,就显示一张图片 if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = ( e1_destroy_index + 1) % 4 #这里是一个小技巧,这样 e1_destroy_index的值只能是0~3 if e1_destroy_index == 0: #当飞机毁灭图片显示完时,就重置飞机 score += 1000 each.reset() if special_enemies: #绘制特殊飞机 for each in special_enemies: if each.active and not each.death: #要还在活动的和之前还没死过的小飞机才能move each.move() screen.blit(each.image, each.rect) else: #飞机毁灭 if not (delay % 3): #每次当delay能整除3的时候,就显示一张图片 if e4_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e4_destroy_index], each.rect) e4_destroy_index = ( e4_destroy_index + 1) % 1 #这里是一个小技巧,这样 e1_destroy_index的值只能是0~3 if e4_destroy_index == 0: #当飞机毁灭图片显示完时,就把小飞机移除出group each.reset( ) #重置飞机位置,并且active = True, death = True special_enemies.remove(each) #把死了的飞机移除出group score += 1000 #绘制子弹 #子弹延时显示设置 if not (delay % 10): #每10帧重置一次图片 bullet_sound.play() if is_double_bullet and bullet2_level > 0: #如果是超级子弹 if bullet2_level == 1: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM #索引+1 elif bullet2_level == 2: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 33, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 30, me.rect.centery)) bullets[bullet2_index + 2].reset(me.rect.midtop) bullet2_index = (bullet2_index + 3) % BULLET2_NUM #索引+1 elif bullet2_level == 3: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 43, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 40, me.rect.centery)) bullets[bullet2_index + 2].reset( (me.rect.centerx - 18, me.rect.centery)) bullets[bullet2_index + 3].reset( (me.rect.centerx + 15, me.rect.centery)) bullet2_index = (bullet2_index + 4) % BULLET2_NUM #索引+1 elif 4 <= bullet2_level < 8: bullets = bullet2 bullets[bullet2_index].reset( (me.rect.centerx - 58, me.rect.centery)) bullets[bullet2_index + 1].reset( (me.rect.centerx + 55, me.rect.centery)) bullets[bullet2_index + 2].reset( (me.rect.centerx - 27, me.rect.centery - 21)) bullets[bullet2_index + 3].reset( (me.rect.centerx + 24, me.rect.centery - 21)) bullets[bullet2_index + 4].reset(me.rect.midtop) bullet2_index = (bullet2_index + 5) % BULLET2_NUM #索引+1 elif bullet2_level >= 8: bullets = bullet3 bullets[bullet3_index].reset( (me.rect.centerx - 58, me.rect.centery)) bullets[bullet3_index + 1].reset( (me.rect.centerx + 55, me.rect.centery)) bullets[bullet3_index + 2].reset( (me.rect.centerx - 27, me.rect.centery - 21)) bullets[bullet3_index + 3].reset( (me.rect.centerx + 24, me.rect.centery - 21)) bullets[bullet3_index + 4].reset(me.rect.midtop) bullet3_index = (bullet3_index + 5) % BULLET3_NUM #索引+1 else: #如果是普通子弹 bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM #索引+1 #显示子弹 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) #子弹碰撞检测 enemy_hit = pygame.sprite.spritecollide( b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False #绘制我方飞机 if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: #飞机毁灭 if not (delay % 3): #每次当delay能整除3的时候,就显示一张图片 if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = ( me_destroy_index + 1) % 4 #这里是一个小技巧,这样 me_destroy_index的值只能是0~3 if me_destroy_index == 0: #当飞机毁灭图片显示完时,就重置飞机 life_num -= 1 me.reset() if 0 < bullet2_level < 8: #如果在8级以下,0级以上,则级数-1 bullet2_level -= 1 elif bullet2_level >= 8: #如果当前超级子弹等级为8级或以上,则级数-2 bullet2_level -= 2 pygame.time.set_timer(INVINCIBLE_TIME_FINISH, 3 * 1000) #调用自定义事件,3秒后结束飞机无敌 #检测我方飞机是否发生碰撞 enemies_down = pygame.sprite.spritecollide( me, enemies, False, pygame.sprite.collide_mask ) #判断me是否与enemies中的任何一个发生碰撞,返回一个列表,里面装了与me发生碰撞的enemies if enemies_down and not me.invincible: #当有敌机坠毁,而且我方飞机不是无敌的时候 me.active = False #我方飞机坠毁 for each in enemies_down: each.active = False #敌方飞机坠毁 #绘制全屏炸弹图片 bomb_text = bomb_font.render("x %d" % bomb_num, True, BLACK) #把text转化成surface bomb_text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) #显示图片 screen.blit(bomb_text, (20 + bomb_rect.width, height - 10 - bomb_text_rect.height)) #显示数字 #绘制剩余生命数量 life_text = life_num_font.render(str(life_num), True, BLACK) #把text转化为surface life_text_rect = life_text.get_rect() screen.blit(life_image, (width - life_image_rect.width - life_text_rect.width, height - 10 - life_image_rect.height)) #显示图片 screen.blit(life_text, (width - life_text_rect.width, height - 10 - life_text_rect.height)) #显示数字 #绘制超级子弹等级 bullet_text = bullet_font.render("Lv:" + str(bullet2_level), True, BLACK) screen.blit(bullet_text, (10, 40)) #绘制分数 score_text = score_font.render("Score : %s" % str(score), True, BLACK) screen.blit(score_text, (10, 5)) #否则,当生命数<0时,就绘制结束画面 elif life_num == 0: pygame.mixer.music.stop() #背景音乐停止 pygame.mixer.stop() #全部音效停止 pygame.time.set_timer(SUPPLY_TIME, 0) #补给发放停止 #读取记录 if not recorded: recorded = True #读取历史最高得分 with open("record.txt", "r") as f: record_score = int(f.read()) #如果玩家得分高于历史最高得分,则分数存档 if score > record_score: record_score = score with open("record.txt", "w") as f: f.write(str(score)) ############################################绘制结束画面###################################################### #绘制字体“Best:” record_score_text = record_score_font.render( "Best : %d" % record_score, True, BLACK) screen.blit(record_score_text, (50, 50)) #绘制字体“Your Score” gameover_text1 = finial_score_font.render("Your Score ", True, BLACK) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = ( width - gameover_text1_rect.width) // 2, height - 500 screen.blit(gameover_text1, gameover_text1_rect) #绘制最终分数 gameover_text2 = finial_score_font.render(str(score), True, BLACK) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = ( width - gameover_text2_rect.width) // 2, height - 450 screen.blit(gameover_text2, gameover_text2_rect) #绘制两个框框 again_image_rect.left, again_image_rect.top = ( width - again_image_rect.width) // 2, height - 390 screen.blit(again_image, again_image_rect) close_image_rect.left, close_image_rect.top = ( width - close_image_rect.width) // 2, height - 320 screen.blit(close_image, close_image_rect) #绘制框框里的字 again_text = gameover_font.render("Try Again", True, BLACK) again_text_rect = again_text.get_rect() again_text_rect.left, again_text_rect.top = ( width - again_text_rect.width) // 2, height - 385 screen.blit(again_text, again_text_rect) close_text = gameover_font.render("End", True, BLACK) close_text_rect = close_text.get_rect() close_text_rect.left, close_text_rect.top = ( width - close_text_rect.width) // 2, height - 315 screen.blit(close_text, close_text_rect) #框框按钮触发 if pygame.mouse.get_pressed()[0]: #如果用户按下鼠标左键 pos = pygame.mouse.get_pos() #获取鼠标坐标 if again_image_rect.left < pos[0] < again_image_rect.right and \ again_image_rect.top < pos[1] < again_image_rect.bottom: #如果按了“Try Again” main() # 调用main函数,重新开始游戏 elif close_image_rect.left < pos[0] < close_image_rect.right and \ close_image_rect.top < pos[1] < close_image_rect.bottom: #如果按了“End” pygame.quit() #退出游戏 sys.exit() #图片延时操作 if not (delay % 5): #每次当delay能整除5时,就变换图片 switch_image = not switch_image delay -= 1 if not delay: delay = 100 #绘制暂停按钮 screen.blit(paused_image, paused_rect) pygame.display.flip() clock.tick(60)
def main(): """ 4.1 -Play the bg music """ pygame.mixer.music.play(-1, 0.0) """ 4.2 -Draw myplane """ me = myplane.MyPlane(bg_size) """ 4.3 -Draw the enemies """ enemies = pygame.sprite.Group() # Draw small enemies small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) # Draw midiume enemies mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) # Draw big enemies big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) # Load boss event but not draw it boss = pygame.sprite.Group() """ 4.4 -Draw bullet and bomb """ # Draw normal bullet bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # Draw super bullet bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM//2): bullet2.append(bullet.Bullet2((me.rect.centerx-33, me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx+30, me.rect.centery))) # Bomb bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_font = pygame.font.SysFont("arial", 48) bomb_num = 3 """ 4.5 -Set the basical parameters """ clock = pygame.time.Clock() # Hit effective images index e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 boss_destory_index = 0 me_destroy_index = 0 # Score score = 0 scoredelta = 0 score_font = pygame.font.Font("font/font.ttf", 36) # Game Pause/Resume button paused = False pause_nor_image = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_image = pygame.image.load("images/pause_pressed.png").convert_alpha() resume_nor_image = pygame.image.load("images/resume_nor.png").convert_alpha() resume_pressed_image = pygame.image.load("images/resume_pressed.png").convert_alpha() paused_rect = pause_nor_image.get_rect() paused_rect.left, paused_rect.top = width - paused_rect.width - 10, 10 paused_image = pause_nor_image # Set the difficult level level = 1 # Supply package send every 15sec bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) life_supply = supply.Life_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME, 15 * 1000) # Superbullet timer DOUBLE_BULLET_TIME = USEREVENT + 1 # Superbullet marker is_double_bullet = False # Invincible timer INVINCIBLE_TIME = USEREVENT + 2 # Life value life_image = pygame.image.load("images/life.png").convert_alpha() life_rect = life_image.get_rect() life_num = 3 # Recorder file opening marker recorded = False # Game over gameover_font = pygame.font.SysFont("arial", 48) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() # Switch image switch_image = True # Delay delay = 100 running = True boss_live = False #Main Loop while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME, 0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME, 15 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_image = resume_pressed_image else: paused_image = pause_pressed_image else: if paused: paused_image = resume_nor_image else: paused_image = pause_nor_image elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() supply_type = choice([0,1,2]) if supply_type == 1: bomb_supply.reset() elif supply_type == 2: life_supply.reset() else: bullet_supply.reset() elif event.type == DOUBLE_BULLET_TIME: is_double_bullet = False pygame.time.set_timer(DOUBLE_BULLET_TIME, 0) elif event.type == INVINCIBLE_TIME: me.invincible = False pygame.time.set_timer(INVINCIBLE_TIME, 0) """ Diffcult level judgment ------------------------------------------------------ """ #the following-line code for test the boss if level >3 and scoredelta > 100000 and score > 500000 and boss_live == False: #if score > 1000 and scoredelta > 6000 and boss_live == False: upgrade_sound.play() # Add 1 boss add_boss(boss, enemies) scoredelta = 0 boss_live = True level -= level if level == 1 and score > 100000: level = 2 upgrade_sound.play() # Add 3 small, 2 mid, 1 big add_small_enemies(small_enemies, enemies, 3) add_mid_enemies(mid_enemies, enemies, 2) add_big_enemies(big_enemies, enemies, 1) # small speed up inc_speed(small_enemies, 1) elif level == 2 and score > 200000: level = 3 upgrade_sound.play() # Add 5 small, 3 mid, 2 big add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # small speed up inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 3 and score > 300000: level = 4 upgrade_sound.play() # Add 5 small, 3 mid, 2 big add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # small speed up inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) elif level == 4 and score > 400000: level = 5 upgrade_sound.play() # Add 5 small, 3 mid, 2 big add_small_enemies(small_enemies, enemies, 5) add_mid_enemies(mid_enemies, enemies, 3) add_big_enemies(big_enemies, enemies, 2) # small speed up inc_speed(small_enemies, 1) inc_speed(mid_enemies, 1) screen.blit(background, (0, 0)) if life_num > -1 and not paused: # keyevent check key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() # Draw bomb and check the supply getting if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image, bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply, me): get_bomb_sound.play() if bomb_num < 5: bomb_num += 1 bomb_supply.active = False # Draw life supply and check the supply getting if life_supply.active: life_supply.move() screen.blit(life_supply.image, life_supply.rect) if pygame.sprite.collide_mask(life_supply, me): get_life_sound.play() if life_num < 5: life_num += 1 life_supply.active = False # Draw superbullet and check the supply getting if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image, bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply, me): get_bullet_sound.play() is_double_bullet = True pygame.time.set_timer(DOUBLE_BULLET_TIME, 18 * 1000) bullet_supply.active = False # launch bullet if not(delay % 10): bullet_sound.play() if is_double_bullet: bullets = bullet2 bullets[bullet2_index].reset((me.rect.centerx-33, me.rect.centery)) bullets[bullet2_index+1].reset((me.rect.centerx+30, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM # enemy hit check for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide(b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies or e in boss: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False # Draw boss for each in boss: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) # Draw healthvalue pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top + 5), \ (each.rect.right, each.rect.top + 5), \ 3) # health value >20% green else red energy_remain = float(each.energy / enemy.Boss.energy) if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + int(each.rect.width * energy_remain), \ each.rect.top - 5), 2) # play music if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: # enemy down if not(delay * 10 % 3): if boss_destory_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[boss_destory_index], each.rect) boss_destory_index = (boss_destory_index + 1) % 6 if boss_destory_index == 0: enemy3_fly_sound.stop() score += 50000 scoredelta += 50000 boss_live = False each.reset() # Draw big enemy for each in big_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) # Draw healthvalue pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 3) # health value >20% green else red energy_remain = float(each.energy / enemy.BigEnemy.energy) if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + int(each.rect.width * energy_remain), \ each.rect.top - 5), 2) # play music if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: # enemy down if not(delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 10000 scoredelta += 10000 each.reset() # Draw middle enemy for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # Draw healthvalue pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 3) # health value >20% green else red energy_remain = float(each.energy / enemy.MidEnemy.energy) if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + int(each.rect.width * energy_remain), \ each.rect.top - 5), 2) else: # enemy down if not(delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 6000 scoredelta += 6000 each.reset() # Draw small enemy for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: # enemy down if not(delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 1000 scoredelta += 1000 each.reset() # Check my collision enemies_down = pygame.sprite.spritecollide(me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.invincible: me.active = False for e in enemies_down: e.active = False # Draw my plane if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: # my plane down if not(delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(INVINCIBLE_TIME, 3 * 1000) # Draw bomb number if bomb_num < 5: bomb_text = bomb_font.render("* %d" % bomb_num, True, LIGHTGREEN) else: bomb_text = bomb_font.render("MAX", True,LIGHTGREEN) text_rect = bomb_text.get_rect() screen.blit(bomb_image, (10, height - 10 - bomb_rect.height)) screen.blit(bomb_text, (20 + bomb_rect.width, height - 5 - text_rect.height)) # Draw remaining life number if life_num: for i in range(life_num): screen.blit(life_image, \ (width-10-(i+1)*life_rect.width, \ height-10-life_rect.height)) # Draw sorce score_text = score_font.render("Score : %s" % str(score), True, LIGHTGREEN) screen.blit(score_text, (10, 5)) # Draw gameover elif life_num == -1: #Stop bgmusic pygame.mixer.music.stop() # Stop sound effct pygame.mixer.stop() # Stop supply pygame.time.set_timer(SUPPLY_TIME, 0) if not recorded: recorded = True # read the highest recorder with open("record.txt", "r") as f: record_score = int(f.read()) # save if player get highest if score > record_score: with open("record.txt", "w") as f: f.write(str(score)) # Draw gameover screen record_score_text = score_font.render("Best : %d" % record_score, True, (255, 255, 255)) screen.blit(record_score_text, (50, 50)) gameover_text1 = gameover_font.render("Your Score", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = \ (width - again_rect.width) // 2, \ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) # Mouse motion check # Mouse left button down if pygame.mouse.get_pressed()[0]: # get mouse position pos = pygame.mouse.get_pos() # restart if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: # recall main function main() # end the game elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: # exit pygame.quit() sys.exit() # Draw pause button screen.blit(paused_image, paused_rect) # switch image if not(delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)
def main(): #设置背景音乐循环播放 pygame.mixer.music.play(-1) # 实例化我方飞机 me = myplane.Plane(bg_size) enemies = pygame.sprite.Group() # 实例化敌方小型飞机并添加到对应敌机组 small_enemies = pygame.sprite.Group() add_small_enemies(small_enemies, enemies, 15) # 实例化敌方中型飞机并添加到对应敌机组 mid_enemies = pygame.sprite.Group() add_mid_enemies(mid_enemies, enemies, 4) # 实例化敌方大型飞机并添加到对应敌机组 big_enemies = pygame.sprite.Group() add_big_enemies(big_enemies, enemies, 2) # 生成普通子弹 bullet1 = [] bullet1_index = 0 BULLET1_NUM = 4 for i in range(BULLET1_NUM): bullet1.append(bullet.Bullet1(me.rect.midtop)) # 生成超级子弹 bullet2 = [] bullet2_index = 0 BULLET2_NUM = 8 for i in range(BULLET2_NUM // 2): bullet2.append(bullet.Bullet2((me.rect.centerx - 33,me.rect.centery))) bullet2.append(bullet.Bullet2((me.rect.centerx + 33,me.rect.centery))) clock = pygame.time.Clock() # 中弹图片索引 e1_destroy_index = 0 e2_destroy_index = 0 e3_destroy_index = 0 me_destroy_index = 0 #统计分数 score = 0 score_font = pygame.font.Font("font/font.ttf",36) paused = False pause_nor_img = pygame.image.load("images/pause_nor.png").convert_alpha() pause_pressed_img = pygame.image.load("images/pause_pressed.png").convert_alpha() resume_nor_img = pygame.image.load("images/resume_nor.png").convert_alpha() resume_pressed_img = pygame.image.load("images/resume_pressed.png").convert_alpha() paused_rect = pause_nor_img.get_rect() paused_rect.left,paused_rect.top = (width - paused_rect.width - 10,10) paused_img = pause_nor_img #设置难度等级 level = 1 #全屏炸弹 bomb_image = pygame.image.load("images/bomb.png").convert_alpha() bomb_rect = bomb_image.get_rect() bomb_num = 3 bomb_font = pygame.font.Font("font/font.ttf",48) #补给包 bullet_supply = supply.Bullet_Supply(bg_size) bomb_supply = supply.Bomb_Supply(bg_size) SUPPLY_TIME = USEREVENT pygame.time.set_timer(SUPPLY_TIME,30 * 1000) #超级子弹 SUPPER_BULLET = USEREVENT + 1 #超级子弹使用标记 is_supper_bullet = False #生命数量 life_image = pygame.image.load("images/life.png").convert_alpha() life_rect = life_image.get_rect() life_num = 3 #解除无敌状态事件 SAFE_TIME = USEREVENT + 2 #用于阻止重复打开文件 recorded = False #游戏结束画面 gameover_font = pygame.font.Font("font/STHUPO.ttf",36) again_image = pygame.image.load("images/again.png").convert_alpha() again_rect = again_image.get_rect() gameover_image = pygame.image.load("images/gameover.png").convert_alpha() gameover_rect = gameover_image.get_rect() # 用于切换图片 switch_image = True # 用于延迟 delay = 100 running = True while running: for event in pygame.event.get(): if event.type == QUIT: pygame.quit() sys.exit() elif event.type == MOUSEBUTTONDOWN: if event.button == 1 and paused_rect.collidepoint(event.pos): paused = not paused if paused: pygame.time.set_timer(SUPPLY_TIME,0) pygame.mixer.music.pause() pygame.mixer.pause() else: pygame.time.set_timer(SUPPLY_TIME,30 * 1000) pygame.mixer.music.unpause() pygame.mixer.unpause() elif event.type == MOUSEMOTION: if paused_rect.collidepoint(event.pos): if paused: paused_img = resume_pressed_img else: paused_img = pause_pressed_img else: if paused: paused_img = resume_nor_img else: paused_img = pause_nor_img elif event.type == KEYDOWN: if event.key == K_SPACE: if bomb_num: bomb_num -= 1 bomb_sound.play() for each in enemies: if each.rect.bottom > 0: each.active = False elif event.type == SUPPLY_TIME: supply_sound.play() if choice([True,False]): bullet_supply.reset() else: bomb_supply.reset() elif event.type == SUPPER_BULLET: is_supper_bullet = False pygame.time.set_timer(SUPPER_BULLET,0) elif event.type == SAFE_TIME: me.safe_time = False pygame.time.set_timer(SAFE_TIME,0) if level == 1 and score > 500: level = 2 upgrade_sound.play() #增加三架小型敌机、两架小型敌机、一架小型敌机 add_small_enemies(small_enemies,enemies,3) add_mid_enemies(mid_enemies,enemies,2) add_big_enemies(big_enemies,enemies,1) #提升小型机的速度 add_speed(small_enemies,1) elif level == 2 and score > 2000: level = 3 upgrade_sound.play() #增加三架小型敌机、两架小型敌机、一架小型敌机 add_small_enemies(small_enemies,enemies,5) add_mid_enemies(mid_enemies,enemies,3) add_big_enemies(big_enemies,enemies,2) #提升小型机的速度 add_speed(small_enemies,1) add_speed(mid_enemies,1) elif level == 3 and score > 5000: level = 4 upgrade_sound.play() #增加三架小型敌机、两架小型敌机、一架小型敌机 add_small_enemies(small_enemies,enemies,5) add_mid_enemies(mid_enemies,enemies,3) add_big_enemies(big_enemies,enemies,2) #提升小型机的速度 add_speed(small_enemies,1) add_speed(mid_enemies,1) elif level == 4 and score > 10000: level = 5 upgrade_sound.play() #增加三架小型敌机、两架小型敌机、一架小型敌机 add_small_enemies(small_enemies,enemies,5) add_mid_enemies(mid_enemies,enemies,3) add_big_enemies(big_enemies,enemies,2) #提升小型机的速度 add_speed(small_enemies,1) add_speed(mid_enemies,1) screen.blit(background, (0, 0)) if life_num and not paused: # 检测用户的键盘操作 key_pressed = pygame.key.get_pressed() if key_pressed[K_w] or key_pressed[K_UP]: me.moveUp() if key_pressed[K_s] or key_pressed[K_DOWN]: me.moveDown() if key_pressed[K_a] or key_pressed[K_LEFT]: me.moveLeft() if key_pressed[K_d] or key_pressed[K_RIGHT]: me.moveRight() #绘制全屏炸弹并检测是否获得 if bomb_supply.active: bomb_supply.move() screen.blit(bomb_supply.image,bomb_supply.rect) if pygame.sprite.collide_mask(bomb_supply,me): get_bomb_sound.play() if bomb_num < 3: bomb_num += 1 bomb_supply.active = False if bullet_supply.active: bullet_supply.move() screen.blit(bullet_supply.image,bullet_supply.rect) if pygame.sprite.collide_mask(bullet_supply,me): get_bullet_sound.play() is_supper_bullet = True pygame.time.set_timer(SUPPER_BULLET,18 * 1000) bullet_supply.active = False # 发射子弹 if not(delay % 10): bullet_sound.play() if is_supper_bullet: bullets = bullet2 bullets[bullet2_index].reset((me.rect.centerx-33, me.rect.centery)) bullets[bullet2_index+1].reset((me.rect.centerx+33, me.rect.centery)) bullet2_index = (bullet2_index + 2) % BULLET2_NUM else: bullets = bullet1 bullets[bullet1_index].reset(me.rect.midtop) bullet1_index = (bullet1_index + 1) % BULLET1_NUM # 检测子弹是否击中敌机 for b in bullets: if b.active: b.move() screen.blit(b.image, b.rect) enemy_hit = pygame.sprite.spritecollide(b, enemies, False, pygame.sprite.collide_mask) if enemy_hit: b.active = False for e in enemy_hit: if e in mid_enemies or e in big_enemies: e.hit = True e.energy -= 1 if e.energy == 0: e.active = False else: e.active = False # 绘制大型敌机 for each in big_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: if switch_image: screen.blit(each.image1, each.rect) else: screen.blit(each.image2, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # 当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.BigEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) # 即将出现在画面中,播放音效 if each.rect.bottom == -50: enemy3_fly_sound.play(-1) else: # 毁灭 if not(delay % 3): if e3_destroy_index == 0: enemy3_down_sound.play() screen.blit(each.destroy_images[e3_destroy_index], each.rect) e3_destroy_index = (e3_destroy_index + 1) % 6 if e3_destroy_index == 0: enemy3_fly_sound.stop() score += 100 each.reset() # 绘制中型敌机: for each in mid_enemies: if each.active: each.move() if each.hit: screen.blit(each.image_hit, each.rect) each.hit = False else: screen.blit(each.image, each.rect) # 绘制血槽 pygame.draw.line(screen, BLACK, \ (each.rect.left, each.rect.top - 5), \ (each.rect.right, each.rect.top - 5), \ 2) # 当生命大于20%显示绿色,否则显示红色 energy_remain = each.energy / enemy.MidEnemy.energy if energy_remain > 0.2: energy_color = GREEN else: energy_color = RED pygame.draw.line(screen, energy_color, \ (each.rect.left, each.rect.top - 5), \ (each.rect.left + each.rect.width * energy_remain, \ each.rect.top - 5), 2) else: # 毁灭 if not(delay % 3): if e2_destroy_index == 0: enemy2_down_sound.play() screen.blit(each.destroy_images[e2_destroy_index], each.rect) e2_destroy_index = (e2_destroy_index + 1) % 4 if e2_destroy_index == 0: score += 20 each.reset() # 绘制小型敌机: for each in small_enemies: if each.active: each.move() screen.blit(each.image, each.rect) else: # 毁灭 if not(delay % 3): if e1_destroy_index == 0: enemy1_down_sound.play() screen.blit(each.destroy_images[e1_destroy_index], each.rect) e1_destroy_index = (e1_destroy_index + 1) % 4 if e1_destroy_index == 0: score += 10 each.reset() # 检测我方飞机是否被撞 enemies_down = pygame.sprite.spritecollide(me, enemies, False, pygame.sprite.collide_mask) if enemies_down and not me.safe_time: me.active = False for e in enemies_down: e.active = False # 绘制我方飞机 if me.active: if switch_image: screen.blit(me.image1, me.rect) else: screen.blit(me.image2, me.rect) else: # 毁灭 if not(delay % 3): if me_destroy_index == 0: me_down_sound.play() screen.blit(me.destroy_images[me_destroy_index], me.rect) me_destroy_index = (me_destroy_index + 1) % 4 if me_destroy_index == 0: life_num -= 1 me.reset() pygame.time.set_timer(SAFE_TIME,3 * 1000) #绘制剩余炸弹数量 bomb_text = bomb_font.render("× {0}".format(str(bomb_num)),True,(255,255,255)) text_rect = bomb_text.get_rect() screen.blit(bomb_image,(10,height - bomb_rect.height - 10)) screen.blit(bomb_text,(20 + bomb_rect.width,height - 5 - text_rect.height)) score_text = score_font.render("score:{0}".format(str(score)),True,(128,128,128)) screen.blit(score_text,(10,5)) #绘制剩余生命数量 if life_num: for i in range(life_num): screen.blit(life_image,(width - 10 - (i + 1) * life_rect.width,height - 10 - life_rect.height)) elif life_num == 0: pygame.mixer.music.stop() pygame.mixer.stop() pygame.time.set_timer(SUPPLY_TIME,0) if not recorded: recorded = True with open ("record.txt","r") as f: record_score = int(f.read()) if score > record_score: with open ("record.txt","w") as f: f.write(str(score)) #绘制结束画面 record_score_text = score_font.render("Best : %d" % record_score, True, (255, 255, 255)) screen.blit(record_score_text, (10, 10)) gameover_text1 = gameover_font.render("小坨,失败乃成功之母", True, (255, 255, 255)) gameover_text1_rect = gameover_text1.get_rect() gameover_text1_rect.left, gameover_text1_rect.top = \ (width - gameover_text1_rect.width) // 2, height // 3 screen.blit(gameover_text1, gameover_text1_rect) gameover_text2 = gameover_font.render(str(score), True, (255, 255, 255)) gameover_text2_rect = gameover_text2.get_rect() gameover_text2_rect.left, gameover_text2_rect.top = \ (width - gameover_text2_rect.width) // 2, \ gameover_text1_rect.bottom + 10 screen.blit(gameover_text2, gameover_text2_rect) again_rect.left, again_rect.top = \ (width - again_rect.width) // 2, \ gameover_text2_rect.bottom + 50 screen.blit(again_image, again_rect) gameover_rect.left, gameover_rect.top = \ (width - again_rect.width) // 2, \ again_rect.bottom + 10 screen.blit(gameover_image, gameover_rect) # 检测用户的鼠标操作 # 如果用户按下鼠标左键 if pygame.mouse.get_pressed()[0]: # 获取鼠标坐标 pos = pygame.mouse.get_pos() # 如果用户点击“重新开始” if again_rect.left < pos[0] < again_rect.right and \ again_rect.top < pos[1] < again_rect.bottom: # 调用main函数,重新开始游戏 main() # 如果用户点击“结束游戏” elif gameover_rect.left < pos[0] < gameover_rect.right and \ gameover_rect.top < pos[1] < gameover_rect.bottom: # 退出游戏 pygame.quit() sys.exit() #绘制暂停按钮 screen.blit(paused_img,paused_rect) # 切换图片 if not(delay % 5): switch_image = not switch_image delay -= 1 if not delay: delay = 100 pygame.display.flip() clock.tick(60)