- plane_main.py
- plane_sprites.py
- images文件夹:游戏中用到的图片
Windows7 + Python3.6 + anaconda3 + pygame
类:
- PlaneGame
- 方法:私有方法
__create_sprites用于创建背景和战机,声明敌机精灵组;start_game用于游戏循环;私有方法__event_handler用于获取键盘事件和定时器事件;私有方法__check_collide用于碰撞检测;私有方法__update_sprites,通过update和draw的连用来达到更新画面的效果,需要注意的是,这个函数中操作的都是精灵组;静态方法__game_over,结束游戏 - 属性:screen, clock, back_group, enemy_group, hero, hero_group
- 方法:私有方法
- BackGround:要营造出战机在不断前进的状态,通过设置背景图不断下降即可。需要用两张背景连续移动。
- 方法:扩展了父类的update和初始化方法
- GameSprite,是BackGround类的父类
- 方法:定义了update方法和初始化方法
- 属性:image, rect, speed
- Hero,继承自GameSprite
- 方法:扩展了父类的初始化方法,重写了父类的update方法。还有自己特有的fire方法,fire方法一次发射三颗子弹:先创建子弹,然后定义子弹的位置,然后把初始化后的子弹使用add方法加入子弹精灵组中
- 属性:bullets,属于精灵组类型
- Bullet,继承自GameSprite
- Enemy,继承自GameSprite
其他:
- 精灵组。先定义精灵,然后将定义好的精灵放入精灵组中。在游戏中出现的都是精灵组。
- 程序从main函数开始执行
- 所谓定时器事件,就是每隔一段时间,去执行一些操作。比如私有方法
__create_sprites,设置了创建敌机和子弹这两个定时器事件 - 在Python OOP中,创建对象后,解释器依次调用对象的
__new__和__init__;在销毁对象时,依次调用kill和__del__
OOP的三大特性:封装,继承,多态
- 类和对象的关系:类只有一个,对象可以有很多个。(飞机图纸和飞机的关系)
- 代码中self的含义:哪一个对象调用的方法,self就是哪一个对象的引用
- 创建对象时,解释器会自动做两件事:为对象分配内存(
__new__方法)和调用对象的初始化方法 - 初始化方法:
__init__(self)- 负责创建类属性
- 负责接收形参:
tom=Cat('Tom')
- 私有属性和私有方法
- 定义:在属性名或方法名之前,加两个下划线就变成了私有
- 私有的含义:在C++的类中,有权限public关键字,public指的是两方面权限:一是由对象在类外直接调用方法;二是在类的内部,由其他方法调用。在Python中,也是如此,私有方法指的是第二种权限。
- Python中的私有并不是真正的私有:
# 假设ClassA中含有私有方法__age
obj=ClassA()
obj.__age # error: no such attribute
obj._ClassA__age # pass
注意:类的内置方法通常在函数名前后都有下划线,比如初始化方法就是一个内置方法
class child(parent)
- 子类拥有父类的所有方法和属性
- 如果父类发生改变,那么子类中继承自父类的方法同样发生改变
- 子类对象不能直接访问父类的私有属性和方法,但是如果父类中本身就可以通过公有方法访问私有数据的话,那么子类对象是可以通过这种途径访问父类私有数据。所以父亲的隐私是不容易被儿子发现的
可以覆盖,可以扩展
- 覆盖:解释器会寻找并自动调用子类的方法
- 扩展:父类提供的功能较少,需要子类进行拓展。这里用到
super类
class BackGround(GameSprite):
def update(self):
# 调用父类实现:垂直移动
super().update()
# 判断是否移出屏幕,如果移出,将图像设置到屏幕上方
if self.rect.y >= SCREEN_RECT.height:
self.rect.y = -self.rect.height
上面的代码中,BackGround类继承自父类GameSprite。在父类中有update方法,但是子类想在这个的基础上新增一些功能,所以用到super
当子类对象想调用一个方法,无奈父类也有同名的方法,那么解释器会使用哪种呢?这时可以通过内置方法__mro__来查看。
关于多态,目前还没找到能清晰表述多态特性的例子。
- 当看到类名.属性名时,这就是类属性,用于记录类的特征。最常用的是记录一个类创建了多少对象。
- 类名.属性名是类属性,对象名.属性名是对象的属性,也称为实例属性。
- 类方法:
- 在定义前加上
@classmethod关键字修饰 - 该函数传入的参数是
cls - 调用类方法不用创建对象
- 在定义前加上
- 使用
@staticmethod修饰 - 不需要创建对象
- 什么情况下使用?当一个方法不需要调用其他方法时(比如该方法只想打印出当前对象的名字),就可以当做静态方法
在游戏设计中的几个要点:
- 定时器事件
- 碰撞检测
- 事件监听
- 游戏循环
- 精灵与精灵组