Python学习日记-第二十四天-飞机大战(敌机出场设计)
系列文章目录
·使用定时器添加敌机
·设计Enemy 类
前言
昨天因为有事,所以没有及时更新
一、使用定时器添加敌机
- 游戏启动后,每隔一秒会出现一架敌机
- 每架敌机向屏幕下方飞行,飞行速度各不相同
- 每架敌机出现的水平位置也不尽相同
当敌机从屏幕飞出,不会再飞回屏幕中
1.1 定时器
·在Python中,可以使用 pygame.time.set_timer()来添加定时器
·所谓的定时器,就是每隔一段时间,去执行一些动作
代码: set_timer(eventid, milliseconds) -> None
·set_timer 可以创建一个事件
·可以在游戏循环的事件监听方法中捕获到该事件
·第1个参数 事件代码需要基于常量pygame.USEREVENT来指定
USEREVENT是一个整数,再增加的事件可以使用 USEREVENT+1 指定,以此类推
·第2个参数是事件触发 间隔 的毫秒值
定时器事件的监听
·通过pygame.event.get()可以获得当前时刻所有的事件列表
·遍历列表并且判断 event.type 是否等于event.id 如果相等,表示定时器事件发生
1.2 定义并监听创建敌机事件
pygame的定时器使用套路非常固定:
- 定义定时器常量——eventid
- 在初始化方法中,调用set_timer方法设置定时器事件
- 在游戏循环中,监听定时器事件
1)定义事件
·在plane_sprites.py的顶部定义 事件常量
这里虽然pygame 提供了一个 pygame.USEREVENT的常量,但是在我们开发时,还是会针对我们的游戏需求,以及特有的事件,定义一个名字更加方便我们理解的事件常量,会更加的合理,所以我们在这里创建了一个 CREAT_ENEMY_EVENT的常量
这里设置的时间是1000,是因为单位是以毫秒计算的,1000毫秒=1秒
再在之前封装好的 event_handler 监听事件方法里面,增加一个判断,最后再控制台观察“敌机出场”是否是间隔一秒出现一次
二、 设计Enemy类
- 游戏启动后,每隔一秒会出现一架敌机
- 每架敌机向屏幕下方飞行,飞行速度各不相同
- 每架敌机出现的水平位置也不尽相同
- 当敌机从屏幕飞出,不会再飞回屏幕中
·初始化方法
指定 敌机图片
随机 敌机的初始位置和初始速度
·重写update方法
判断是否飞出屏幕,如果是,从精灵族删除
2.1 敌机类的准备
代码:
class Enemy(GameSprite):"""敌机精灵"""def __init__(self):# 1.调用父类方法,创建敌机精灵,同时指定敌机图片super().__init__("./images/enemy1.png")# 2.指定敌机的初始随机速度# 3.指定敌机的初始随机位置passdef update(self):# 1. 调用父类方法,保持垂直方向的飞行super().update()# 2. 判断是否飞出屏幕,飞出了,就冲精灵组删除敌机if self.rect.y >= SCREEN_RECT.height:print("飞出屏幕,需要从精灵组删除")
2.2 创建敌机
演练步骤
1. 在__create_sprites,添加敌机精灵组
·敌机是定时被创建的,因此在初始化方法中,不需要创建敌机
2. 在__event_handler,创建敌机,并且添加到精灵组
·调用精灵组的 add 方法可以像精灵族添加精灵
3. 在 __update_sprites,让敌机精灵组调用update和draw方法
代码:
import pygame
from plane_sprites import *class PlaneGame(object):"""飞机大战主游戏"""def __init__(self):print("游戏初始化")# 1.创建游戏的窗口self.screen = pygame.display.set_mode(SCREEN_RECT.size)# 2.创建游戏的时钟self.clock = pygame.time.Clock# 3.调用私有方法,精灵和精灵组的创建self.__create_sprites()# 4. 设置定时器事件-创建敌机 1spygame.time.set_timer(CREATE_ENEMY_EVENT, 1000)def __create_sprites(self):# 创建背景精灵和精灵组bg1 = Background()bg2 = Background(True)self.back_group = pygame.sprite.Group(bg1, bg2)# 创建敌机的精灵组self.enemy_group = pygame.sprite.Group()def start_game(self):print("游戏开始...")while True:# 1.设置刷新帧率self.clock().tick(FRAME_PER_SEC)# 2.事件监听self.__event_handler()# 3.碰撞检测self.__check_collide()# 4.更新/绘制精灵组self.__update_sprites()# 5.更新显示pygame.display.update()def __event_handler(self):for event in pygame.event.get():# 判断是否退出游戏if event.type == pygame.QUIT:PlaneGame.__game_over()elif event.type == CREATE_ENEMY_EVENT:print("敌机出场")# 创建敌机精灵enemy = Enemy()# 将敌机精灵添加到敌机精灵组self.enemy_group.add(enemy)def __check_collide(self):passdef __update_sprites(self):self.back_group.update()self.back_group.draw(self.screen)self.enemy_group.update()self.enemy_group.draw(self.screen)@staticmethoddef __game_over():print("游戏结束")pygame.quit()exit()if __name__ == '__main__':# 创建游戏对象game = PlaneGame()# 启动游戏
game.start_game()
运行结果:
屏幕每间隔1秒钟,就会生出一架敌机
2.3 随机敌机位置和速度
1. 导入模块(随机速度)
·在导入模块时,建议 按照以下顺序导入
- 官方标准模块导入
- 第三方模块导入
- 应用程序导入
·修改 plane_sprites.py增加random的导入(random模块 在Python中是数字随机,之前有讲过的,random模块时官方标准模块)
import random
运行结果:
敌机的速度都是随机1 - 3了
2. 随机位置
敌机的初始位置x,y的值都是要设置的,通过上面的图解可以了解清楚
使用pygame.Rect 提供的bottom属性,在指定敌机初始位置时,会比较方便
·bottom = y + height
·y = bottom - height
操作:
代码:
self.rect.bottom = 0max_x = SCREEN_RECT.width - self.rect.width
self.rect.x = random.randint(0, max_x)
运行结果:
2.4 移出屏幕销毁敌机(清除内存)
·敌机移出屏幕之后,如果没有碰撞到英雄,敌机的历史使命结束
·需要从敌机组删除,否则会造成内存浪费
检测敌机被销毁
·__del__内置方法会在对象被销毁前调用,在开发中,可以用于判断对象是否被销毁
·判断敌机是否飞出屏幕,如果是,调用kill() 方法从所有组中删除
代码:
def update(self):# 1. 调用父类方法,保持垂直方向的飞行super().update()# 2. 判断是否飞出屏幕,飞出了,就冲精灵组删除敌机if self.rect.y >= SCREEN_RECT.height:print("飞出屏幕,需要从精灵组删除")self.kill()
总结
关于敌机出场的设计就已经设计完成,目前所有的代码总结一下:
1. plane_sprites.py:
import random
import pygame# 屏幕大小的常量
SCREEN_RECT = pygame.Rect(0, 0, 480, 700)
# 定义刷新帧率
FRAME_PER_SEC = 60
# 创建敌机的定时器常量
CREATE_ENEMY_EVENT = pygame.USEREVENTclass GameSprite(pygame.sprite.Sprite):"""飞机大战游戏精灵"""def __init__(self, image_name, speed=1):# 调用父类的初始化方法super().__init__()# 定义对象的属性self.image = pygame.image.load(image_name)self.rect = self.image.get_rect()self.speed = speeddef update(self):# 在屏幕的垂直方向上移动self.rect.y += self.speedclass Background(GameSprite):"""游戏背景精灵"""def __init__(self, is_alt=False):# 1.调用父类方法实现精灵的创建(images/rect/speed)super().__init__("./images/background.png")# 2.判断是否是交替图像,如果是,需要设置初始位置if is_alt:self.rect.y = -self.rect.heightdef update(self):# 1.调用父类的方法实现(垂直在屏幕方向向上移动)super().update()# 2.判断是否移出屏幕,如果移出屏幕,将图像设置到屏幕上方if self.rect.y >= SCREEN_RECT.height:self.rect.y = -self.rect.heightclass Enemy(GameSprite):"""敌机精灵"""def __init__(self):# 1.调用父类方法,创建敌机精灵,同时指定敌机图片super().__init__("./images/enemy1.png")# 2.指定敌机的初始随机速度1 ~ 3self.speed = random.randint(1, 3)# 3.指定敌机的初始随机位置self.rect.bottom = 0max_x = SCREEN_RECT.width - self.rect.widthself.rect.x = random.randint(0, max_x)def update(self):# 1. 调用父类方法,保持垂直方向的飞行super().update()# 2. 判断是否飞出屏幕,飞出了,就冲精灵组删除敌机if self.rect.y >= SCREEN_RECT.height:print("飞出屏幕,需要从精灵组删除")self.kill()
2. plane_main.py
import pygame
from plane_sprites import *class PlaneGame(object):"""飞机大战主游戏"""def __init__(self):print("游戏初始化")# 1.创建游戏的窗口self.screen = pygame.display.set_mode(SCREEN_RECT.size)# 2.创建游戏的时钟self.clock = pygame.time.Clock# 3.调用私有方法,精灵和精灵组的创建self.__create_sprites()# 4. 设置定时器事件-创建敌机 1spygame.time.set_timer(CREATE_ENEMY_EVENT, 1000)def __create_sprites(self):# 创建背景精灵和精灵组bg1 = Background()bg2 = Background(True)self.back_group = pygame.sprite.Group(bg1, bg2)# 创建敌机的精灵组self.enemy_group = pygame.sprite.Group()def start_game(self):print("游戏开始...")while True:# 1.设置刷新帧率self.clock().tick(FRAME_PER_SEC)# 2.事件监听self.__event_handler()# 3.碰撞检测self.__check_collide()# 4.更新/绘制精灵组self.__update_sprites()# 5.更新显示pygame.display.update()def __event_handler(self):for event in pygame.event.get():# 判断是否退出游戏if event.type == pygame.QUIT:PlaneGame.__game_over()elif event.type == CREATE_ENEMY_EVENT:print("敌机出场")# 创建敌机精灵enemy = Enemy()# 将敌机精灵添加到敌机精灵组self.enemy_group.add(enemy)def __check_collide(self):passdef __update_sprites(self):self.back_group.update()self.back_group.draw(self.screen)self.enemy_group.update()self.enemy_group.draw(self.screen)@staticmethoddef __game_over():print("游戏结束")pygame.quit()exit()if __name__ == '__main__':# 创建游戏对象game = PlaneGame()# 启动游戏
game.start_game()
目前主程序运行结果:
敌机随机从屏幕上方飞出,速度设置的是(1-3)之间的随机速度,飞出屏幕之后自动销毁
Python学习日记-第二十四天-飞机大战(敌机出场设计)相关推荐
- Python学习日记-第二十六天-飞机大战(发射子弹和碰撞检测)
系列文章目录 1.发射子弹 2.碰撞检测 一.发射子弹 1.1 添加发射子弹事件 Pygame的定时器使用套路非常固定: 定义定时器常量--eventtid 在初始化方法中,调用set_timer ...
- Python学习日记-第二十九天-tcp(客户端)
系列文章目录 tcp介绍 tcp特点 tcp客户端 一.tcp介绍 Tcp协议,传输控制协议是一种面向连接的.可靠的.基于字节流的传输层通信协议,由IETF的RFC 793定义 TCP通信需要经过创建 ...
- Python学习日记-第十四天-面向对象练习
前言 今天主要是针对昨天学习的面向对象,进行两个练习. 一个是添加家具的练习 另一个是士兵开枪的练习 练习1: 添加家具 需求: 1. 房子 house 有户型,总面积和家具名称列表 ·新房子没有 ...
- Python学习日记(二十四) 继承
继承 什么是继承?就是一个派生类(derived class)继承基类(base class)的字段和方法.一个类可以被多个类继承;在python中,一个类可以继承多个类. 父类可以称为基类和超类,而 ...
- Python学习日记(三十四) Mysql数据库篇 二
外键(Foreign Key) 如果今天有一张表上面有很多职务的信息 我们可以通过使用外键的方式去将两张表产生关联 这样的好处能够节省空间,比方说你今天的职务名称很长,在一张表中就要重复的去写这个职务 ...
- Python学习笔记第二十九天(N维数组(ndarray))
Python学习笔记第二十九天 N维数组(ndarray) 构建阵列 索引阵列 ndarray的内部内存布局 阵列属性 内存布局 数据类型 其他属性 阵列接口 ctypes外部功能接口 Array方法 ...
- python学习的第二十五天:对PDF文件的读写操作
文章目录 python学习的第二十五天:对PDF文件的读写操作 对Excel操作的补充 python的实用方法 获取指定文件下的所有内容 shutil模块(封装了高级的文件操作函数) PDF的相关操作 ...
- Python学习日记-第二十三天-飞机大战(游戏背景设计思路)
系列文章目录 目标 ·背景简体滚动的思路确定 ·显示游戏背景 前言 这一章节是讲述的飞机大战游戏背景的设计思路细节. 一.背景简体滚动的思路确定 ·游戏启动后,背景图像 会连续不断的向下移动 ·视觉上 ...
- Python学习日记(二十二) 初识面向对象
引子 假设我们要开发一个关于飞机大战的游戏,那么游戏的里面就会有两个角色,分别是属于玩家操控的战机和敌方的战机,并且两个战机都有不同的技能或攻击方式,现在我们用自己目前所学的去写出下面的这些代码: d ...
最新文章
- cop2000计算机组成原理,COP2000计算机组成原理-南昌大学网络教学平台.doc
- python学习笔记(生成xml)
- Hive的基本操作-创建外部表
- 女人赢了 未来500万年男性将灭绝
- 数据库外键约束的几种方法及区别
- 鹤峰:美丽的茶乡—— 舞狮篇
- python-循环语句基础知识
- SAP License: 发票校验前收货后是否能更改物料价格
- C++ 中的动态库和静态库(Windows)
- 计算机三级权限管理方法,Serv―U 三级用户权限机制及配置一例
- 可替换MPS MP2451的高压DCDC芯片FS2451助力智能电表设计40V0.5A降压IC
- Fiona简介及Shapefile数据读取
- 研究将有pid和id的ListMapString,Map组成树
- 信息系统项目管理师必背核心考点(二十一)可交付成果
- 2015年基金公司排名排行榜,基金公司排名2015一览
- 熟练的运用计算机英语怎么说,熟练用英语怎么说
- 回路电感详细介绍(环路电感)
- 手动查看和删除IPC未释放的资源
- Unity连接SQLServer数据库报错找不到System.Data.dll
- 小班计算机游戏教案,小班游戏教案
热门文章
- html图片中加入js,javascript如何添加图片?
- 登录界面更换验证码图片
- XP真的老了,换了吧
- [RK3288][Android6.0] 移植笔记 --- Camera IC OV5640添加
- 微信网页开发(10)--扫一扫功能接口
- springboot在yml配置文件中配置类的属性笔记
- vlookup多项匹配_VLOOKUP函数一对多查找,掌握方法后就是这么简单
- MYSQL数据库设计试卷b_MySQL数据库设计与应用智慧树期末考试免费答案
- 基于SSM框架的云图库系统的设计与实现
- ElasticsearchTemplate 的API