Python版飞机大战程序代码(pygame),详细讲解,手把手教学

懒大王爱吃狼 2024-07-28 11:05:01 阅读 71

0、Python版飞机大战程序代码

需要Python学习资料的朋友可以戳资料哦!

在这里插入图片描述

代码1:

<code> 1 import random 2 import pygame 3

4 # 屏幕大小的常量

5 SCREEN\_RECT = pygame.Rect(0, 0, 480, 700)

6 # 刷新的帧率

7 FRAME\_PER\_SEC = 60

8 # 创建敌机的定时器常量

9 CREATE\_ENEMY\_EVENT = pygame.USEREVENT 10 # 英雄发射子弹事件

11 HERO\_FIRE\_EVENT = pygame.USEREVENT+1

12 #子弹速度

13 BULLET\_SPEED = -2.5

14

15

16 class GameSprite(pygame.sprite.Sprite): 17 """"飞机大战游戏精灵"""

18

19 def \_\_init\_\_(self, image\_name, speed = 1):

20 # 调用父亲的初始化方法

21 super().\_\_init\_\_()

22 # 定义对象的属性

23 self.image = pygame.image.load(image\_name) 24 self.rect = self.image.get\_rect() 25 self.speed = speed 26

27 def update(self): 28 #在屏幕的垂直方向上移动

29 self.rect.y += self.speed 30

31

32 class Background(GameSprite): 33 """"游戏背景精灵"""

34

35 def \_\_init\_\_(self, is\_alt = False): 36 # 1.调用父类构造方法

37 super().\_\_init\_\_("./images/background.png")

38 # 2.判断是否与前图像循环重合,若否,则需重新设置初始位置

39 if is\_alt: 40 self.rect.y = -self.rect.height

41

42

43 def update(self): 44 # 1.调用父类的方法,,,注意super后面要加括号!!!

45 super().update()

46 # 2.判断是否移出屏幕

47 if self.rect.y >= SCREEN\_RECT.height: 48 self.rect.y = -self.rect.height

49

50

51 class Enemy(GameSprite): 52 """"敌机精灵"""

53

54 def \_\_init\_\_(self):

55 # 1.调用父类方法,创建敌机精灵

56 super().\_\_init\_\_("./images/enemy1.png")

57 # 2. 指定敌机的初始随机速度 1-2-3

58 self.speed = random.randint(1,3)

59 # 3.指定敌机的初始随机位置

60 self.rect.bottom = 0 61

62 max\_x = SCREEN\_RECT.width - self.rect.width 63 self.rect.x = random.randint(0, max\_x) 64

65

66 def update(self): 67

68 # 1.调用父类方法,保持垂直方向的飞行

69 super().update()

70 # 2.判断是否非出屏幕,如果是,需要从精灵组删除敌机

71 if self.rect.y >= SCREEN\_RECT.height: 72 #print("飞出屏幕,需要从精灵组删除...")

73 # kill方法可以将精灵从精灵组中移除

74 self.kill()

75

76 def \_\_del\_\_(self):

77 #print("敌机挂了%s" %self.rect)

78 pass

79

80

81 class Hero(GameSprite): 82 """英雄精灵"""

83

84 def \_\_init\_\_(self):

85 # 1.调用父类方法,设置image和speed

86 super().\_\_init\_\_("./images/me1.png", speed = 0) 87 self.speed1 = 0 88 # 2.设置英雄的初始位置

89 self.rect.centerx = SCREEN\_RECT.centerx 90 self.rect.bottom = SCREEN\_RECT.bottom - 100

91 # 3.创建子弹精灵组

92 self.bullets = pygame.sprite.Group() 93

94 def update(self): 95 #(错误的判断句,会导致一旦出界就很难再恢复回来)if 0 <= self.rect.x <= SCREEN\_RECT.width - self.rect.width:

96 self.rect.x += self.speed 97 if self.rect.x < 0: 98 self.rect.x = 0 99 elif self.rect.right > SCREEN\_RECT.width:

100 self.rect.right = SCREEN\_RECT.width

101

102 self.rect.y += self.speed1

103 if self.rect.y < 0:

104 self.rect.y = 0

105 elif self.rect.bottom > SCREEN\_RECT.height:

106 self.rect.bottom = SCREEN\_RECT.height

107

108

109 def fire(self):

110 #print("发射子弹")

111 # 1.创建子弹精灵

112 bullet = Bullet()

113 # 2.设置精灵位置

114 bullet.rect.bottom = self.rect.y

115 bullet.rect.centerx = self.rect.centerx

116 # 3.将精灵添加到精灵组

117 self.bullets.add(bullet)

118

119

120 class Bullet(GameSprite):

121 """"子弹精灵"""

122

123 def \_\_init\_\_(self):

124 # 调用父类方法

125 super().\_\_init\_\_("./images/bullet1.png", BULLET\_SPEED)

126

127 def update(self):

128 super().update()

129 if self.rect.bottom < 0:

130 self.kill()

131

132 def \_\_del\_\_(self):

133 #print("子弹被销毁")

134 pass

View Code

代码2:

<code> 1 from plane\_sprites import \*

2 # 游戏主程序

3

4 class PlaneGame(object): 5 """"飞机大战主游戏"""

6

7 def \_\_init\_\_(self):

8 print("游戏初始化")

9

10 # 1.创建游戏的窗口

11 self.screen = pygame.display.set\_mode(SCREEN\_RECT.size) 12 # 2.创建游戏的时钟

13 self.clock = pygame.time.Clock() 14 # 3.调用私有方法,精灵和精灵组的创建

15 self.\_\_create\_sprites()

16 # 4.设置定时器事件——创建敌机 1s

17 pygame.time.set\_timer(CREATE\_ENEMY\_EVENT,1000)

18 pygame.time.set\_timer(HERO\_FIRE\_EVENT, 300)

19

20 def \_\_create\_sprites(self):

21 # 创建背景精灵和精灵组

22 bg1 = Background() 23 bg2 = Background(True) 24 self.back\_group = pygame.sprite.Group(bg1, bg2) 25 # 创建敌机精灵

26 self.enemy\_group = pygame.sprite.Group() 27 # 创建英雄精灵

28 self.hero = Hero() 29 self.hero\_group = pygame.sprite.Group(self.hero) 30

31

32 def start\_game(self): 33 print("游戏开始...")

34

35 while True: 36 # 1.设置刷新帧率

37 self.clock.tick(FRAME\_PER\_SEC)

38 # 2.事件监听

39 self.\_\_event\_handler()

40 # 3.碰撞检测

41 self.\_\_check\_collide()

42 # 4.更新/绘制精灵组

43 self.\_\_update\_sprites()

44 # 5.更新显示

45 pygame.display.update()

46

47

48 def \_\_event\_handler(self):

49 for event in pygame.event.get(): 50 #判断是否退出游戏

51 if event.type == pygame.QUIT: 52 PlaneGame.\_\_game\_over()

53 elif event.type == CREATE\_ENEMY\_EVENT: 54 #print("敌机出现。。。")

55 # 创建敌机精灵

56 enemy = Enemy() 57 # 将敌机精灵添加到敌机精灵组中

58 self.enemy\_group.add(enemy)

59 elif event.type == HERO\_FIRE\_EVENT: 60 self.hero.fire()

61

62 # elif event.type == pygame.KEYDOWN and event.key == pygame. K\_RIGHT:

63 # print("向右移动")

64

65 # 使用键盘提供的方法获得按键元组

66 keys\_pressed = pygame.key.get\_pressed() 67 #判断元组中对应的按键索引值

68 if keys\_pressed\[pygame.K\_RIGHT\]: 69 self.hero.speed = 2

70 elif keys\_pressed\[pygame.K\_LEFT\]: 71 self.hero.speed = -2

72 elif keys\_pressed\[pygame.K\_DOWN\]: 73 self.hero.speed1 = 2

74 elif keys\_pressed\[pygame.K\_UP\]: 75 self.hero.speed1 = -2

76 else:

77 self.hero.speed = 0 78 self.hero.speed1 = 0 79

80

81 def \_\_check\_collide(self):

82 # 1.子弹摧毁敌机

83 pygame.sprite.groupcollide(self.hero.bullets, self.enemy\_group, True, True)

84 # 2.敌机撞毁英雄

85 enenmy = pygame.sprite.spritecollide(self.hero, self.enemy\_group, True) 86 if len(enenmy) > 0: 87 self.hero.kill()

88 print("飞机被撞毁,任务失败!")

89 PlaneGame.\_\_game\_over()

90

91 def \_\_update\_sprites(self):

92 # 更新显示背景

93 self.back\_group.update()

94 self.back\_group.draw(self.screen)

95 # 更新显示敌机

96 self.enemy\_group.update()

97 self.enemy\_group.draw(self.screen)

98 # 更新显示英雄

99 self.hero\_group.update()

100 self.hero\_group.draw(self.screen)

101 # 更新显示子弹

102 self.hero.bullets.update()

103 self.hero.bullets.draw(self.screen)

104

105 @staticmethod

106 def \_\_game\_over():

107 print("游戏结束")

108

109 pygame.quit()

110 exit()

111

112 if \_\_name\_\_ == '\_\_main\_\_':

113 #创建游戏对象

114 game = PlaneGame()

115 #启动游戏

116 game.start\_game()

View Code

最终呈现结果:

1、准备工作

1.1 图像素材

为了实现这个游戏,我们需要一些图片(png格式)。其中包括:玩家飞机、敌机、背景图等等。

1.2 打开pycharm,导入pygame包

pygame是python中一个第三方库,具有良好的游戏开发性能,功能强大且内容十分丰富,具体请百度或者参考该博客: https://blog.csdn.net/qq_38526635/article/details/82688786

1.3 pygame绘制游戏窗口

1) pygame中的坐标系以左上角为原点,提供了一个类pygame.Rect用于描述矩形区域.

Rect对象的常见属性:x, y, left, top, bottom, right, center, centerx, centery, size, width, height.

<code>1 Rect(x, y, width, height) →Rect

2)pygame.display用于创建与管理窗口

<code>1 # 创建游戏主窗口

2 screen = pygame.display.set\_mode((480, 700))

3)图像绘制

<code> 1 import pygame 2

3 游戏初始化标准句,Rect对象可以不用

4 pygame.init()

5

6 # 创建游戏的窗口 480 \* 700

7 screen = pygame.display.set\_mode((480, 700))

8

9 # 绘制背景图像

10 bg = pygame.image.load("./images/background.png")

11 screen.blit(bg, (0, 0))

12 # pygame.display.update()

13

14 # 绘制英雄的飞机

15 hero = pygame.image.load("./images/me1.png")

16 screen.blit(hero, (150, 300))

17

18 # 可以在所有绘制工作完成之后,统一调用update方法

19 pygame.display.update()

20

21 while True:

22 pass

23

24 pygame.quit()

View Code

1.4 游戏循环

1)pygame.time.Clock用于刷新帧率

要使用时钟对象需要两步:①在游戏初始化创建一个时钟对象;②在游戏循环中让时钟对象调用tick(帧率)方法

2)pygame.event.get()可以得到用户当前所做动作的时间列表(代码相对比较固定)

<code> 1 #游戏循环

2 while True: 3 #设置帧率

4 clock.tick(60)

5 #事件监听

6 for event in pygame.event.get(): 7 #判断用户是否点击了关闭按钮

8 if event.type == pygame.QUIT: 9 print("退出游戏。。。")

10 pygame.quit()

11 #直接退出系统

12 exit()

View Code

2、游戏初始化

该游戏的大体框架是两部分内容:一部分是基于pygame.sprite.Sprite这个父类,创建各种各样的派生类,比如子弹类,敌机类。第二部分是创建主程序类PlaneGame,使用前面各种类来实现具体的游戏功能。

首先先来看类PlaneGame的创建过程:

2.1 创建类PlaneGame的构造函数

1 class PlaneGame(object):

2

3 def \_\_init\_\_(self):

4 print("游戏初始化")

2.2 创建游戏的窗口

1 # 屏幕大小的常量

2 SCREEN\_RECT = pygame.Rect(0, 0, 480, 700)

3 ...

4 self.screen = pygame.display.set\_mode(SCREEN\_RECT.size)

2.3创建游戏时钟

1 self.clock = pygame.time.Clock()

2.4调用私有方法,精灵和精灵组的创建

1 self.\_\_create\_sprites()

2.5设置定时器事件

<code> 1 # 创建敌机的定时器常量

2 CREATE\_ENEMY\_EVENT = pygame.USEREVENT 3 # 英雄发射子弹事件

4 HERO\_FIRE\_EVENT = pygame.USEREVENT+1

5

6 class PlaneGame(object): 7 def \_\_init\_\_(self):

8 ...

9 pygame.time.set\_timer(CREATE\_ENEMY\_EVENT,1000)

10 pygame.time.set\_timer(HERO\_FIRE\_EVENT, 300)

View Code

3、创建精灵组

3.1创建精灵父类GameSprite

继承自pygame.sprite.Sprite类,包含image、rect、spped=1等属性和update()方法。

<code> 1 class GameSprite(pygame.sprite.Sprite): 2

3 def \_\_init\_\_(self, image\_name, speed = 1):

4 # 调用父亲的初始化方法

5 super().\_\_init\_\_()

6 # 定义对象的属性

7 self.image = pygame.image.load(image\_name) 8 self.rect = self.image.get\_rect() 9 self.speed = speed

10

11 def update(self):

12 #在屏幕的垂直方向上移动

13 self.rect.y += self.speed

View Code

3.2 创建游戏背景精灵类

采用一张图循环拼接构成游戏背景,故需要在主程序中生成两个背景精灵对象。

<code> 1 class Background(GameSprite): 2

3 def \_\_init\_\_(self, is\_alt = False): 4 # 1.调用父类构造方法

5 super().\_\_init\_\_("./images/background.png")

6 # 2.判断是否与前图像循环重合,若否,则需重新设置初始位置

7 if is\_alt: 8 self.rect.y = -self.rect.height

9

10

11 def update(self):

12 # 1.调用父类的方法,,,注意super后面要加括号!!!

13 super().update()

14 # 2.判断是否移出屏幕

15 if self.rect.y >= SCREEN\_RECT.height:

16 self.rect.y = -self.rect.height

View Code

3.3 创建敌机精灵类

其实质是一秒产生一架敌机并将其随机从上方某处以1,2或者3的速度落下。当飞出屏幕外注意使用self.kill()自我销毁。

<code> 1 class Enemy(GameSprite): 2

3 def \_\_init\_\_(self):

4 # 1.调用父类方法,创建敌机精灵

5 super().\_\_init\_\_("./images/enemy1.png")

6 # 2. 指定敌机的初始随机速度 1-2-3

7 self.speed = random.randint(1,3)

8 # 3.指定敌机的初始随机位置

9 self.rect.bottom = 0

10

11 max\_x = SCREEN\_RECT.width - self.rect.width

12 self.rect.x = random.randint(0, max\_x)

13

14

15 def update(self):

16

17 # 1.调用父类方法,保持垂直方向的飞行

18 super().update()

19 # 2.判断是否非出屏幕,如果是,需要从精灵组删除敌机

20 if self.rect.y >= SCREEN\_RECT.height:

21 #print("飞出屏幕,需要从精灵组删除...")

22 # kill方法可以将精灵从精灵组中移除

23 self.kill()

24

25 def \_\_del\_\_(self):

26 #print("敌机挂了%s" %self.rect)

27 pass

View Code

3.4 创建子弹类

子弹类飞出屏幕外需要自我销毁

<code> 1 class Bullet(GameSprite): 2

3 def \_\_init\_\_(self):

4 # 调用父类方法

5 super().\_\_init\_\_("./images/bullet1.png", BULLET\_SPEED)

6

7 def update(self): 8 super().update()

9 if self.rect.bottom < 0:

10 self.kill()

11

12 def \_\_del\_\_(self):

13 #print("子弹被销毁")

14 pass

View Code

3.5 创建英雄类

英雄类多了一个fire()方法,并且内部包含子弹类

<code> 1 class Hero(GameSprite): 2

3 def \_\_init\_\_(self):

4 # 1.调用父类方法,设置image和speed

5 super().\_\_init\_\_("./images/me1.png", speed = 0) 6 self.speed1 = 0 7 # 2.设置英雄的初始位置

8 self.rect.centerx = SCREEN\_RECT.centerx 9 self.rect.bottom = SCREEN\_RECT.bottom - 100

10 # 3.创建子弹精灵组

11 self.bullets = pygame.sprite.Group()

12

13 def update(self):

14 #(错误的判断句,会导致一旦出界就很难再恢复回来)if 0 <= self.rect.x <= SCREEN\_RECT.width - self.rect.width:

15 self.rect.x += self.speed

16 if self.rect.x < 0:

17 self.rect.x = 0

18 elif self.rect.right > SCREEN\_RECT.width:

19 self.rect.right = SCREEN\_RECT.width

20

21 self.rect.y += self.speed1

22 if self.rect.y < 0:

23 self.rect.y = 0

24 elif self.rect.bottom > SCREEN\_RECT.height:

25 self.rect.bottom = SCREEN\_RECT.height

26

27

28 def fire(self):

29 #print("发射子弹")

30 # 1.创建子弹精灵

31 bullet = Bullet()

32 # 2.设置精灵位置

33 bullet.rect.bottom = self.rect.y

34 bullet.rect.centerx = self.rect.centerx

35 # 3.将精灵添加到精灵组

36 self.bullets.add(bullet)

View Code

3.6 在主程序中创建精灵(组)

<code> 1 class PlaneGame(object): 2

3 def \_\_init\_\_(self):

4 ...

5

6 def \_\_create\_sprites(self):

7 # 创建背景精灵和精灵组

8 bg1 = Background() 9 bg2 = Background(True)

10 self.back\_group = pygame.sprite.Group(bg1, bg2)

11 # 创建敌机精灵

12 self.enemy\_group = pygame.sprite.Group()

13 # 创建英雄精灵

14 self.hero = Hero()

15 self.hero\_group = pygame.sprite.Group(self.hero)

View Code

4、开始游戏

首先令FRAME_PER_SEC = 60,调用self.clock.tick(FRAME_PER_SER)设置帧率为60

<code> 1 class PlaneGame(object): 2 def \_\_init\_\_(self):

3 ...

4

5 def \_\_create\_sprites(self):

6 ...

7

8 def start\_game(self): 9 while True:

10 # 1.设置刷新帧率

11 self.clock.tick(FRAME\_PER\_SEC)

12 # 2.事件监听

13 self.\_\_event\_handler()

14 # 3.碰撞检测

15 self.\_\_check\_collide()

16 # 4.更新/绘制精灵组

17 self.\_\_update\_sprites()

18 # 5.更新显示

19 pygame.display.update()

View Code

4.1 事件监听

<code> 1 def \_\_event\_handler(self):

2 for event in pygame.event.get(): 3 #判断是否退出游戏

4 if event.type == pygame.QUIT: 5 PlaneGame.\_\_game\_over()

6 elif event.type == CREATE\_ENEMY\_EVENT: 7 #print("敌机出现。。。")

8 # 创建敌机精灵

9 enemy = Enemy()

10 # 将敌机精灵添加到敌机精灵组中

11 self.enemy\_group.add(enemy)

12 elif event.type == HERO\_FIRE\_EVENT:

13 self.hero.fire()

14

15 # 使用键盘提供的方法获得按键元组

16 keys\_pressed = pygame.key.get\_pressed()

17 #判断元组中对应的按键索引值

18 if keys\_pressed\[pygame.K\_RIGHT\]:

19 self.hero.speed = 2

20 elif keys\_pressed\[pygame.K\_LEFT\]:

21 self.hero.speed = -2

22 elif keys\_pressed\[pygame.K\_DOWN\]:

23 self.hero.speed1 = 2

24 elif keys\_pressed\[pygame.K\_UP\]:

25 self.hero.speed1 = -2

26 else:

27 self.hero.speed = 0

28 self.hero.speed1 = 0

View Code

具体参考pygame.event.get()方法使用

4.2 碰撞检测

pygame.sprite.groupcollide()用于两个精灵群的碰撞

pygame.sprite.spritecollide()用于精灵和精灵群的碰撞

<code> 1 def \_\_check\_collide(self):

2

3 # 1.子弹摧毁敌机

4 pygame.sprite.groupcollide(self.hero.bullets, self.enemy\_group, True, True)

5

6 # 2.敌机撞毁英雄

7 enenmy = pygame.sprite.spritecollide(self.hero, self.enemy\_group, True) 8 if len(enenmy) > 0: 9 self.hero.kill()

10 print("飞机被撞毁,任务失败!")

11 PlaneGame.\_\_game\_over()

View Code

4.3 更新/绘制精灵组

<code> 1 def \_\_update\_sprites(self):

2 # 更新显示背景

3 self.back\_group.update()

4 self.back\_group.draw(self.screen)

5 # 更新显示敌机

6 self.enemy\_group.update()

7 self.enemy\_group.draw(self.screen)

8 # 更新显示英雄

9 self.hero\_group.update()

10 self.hero\_group.draw(self.screen)

11 # 更新显示子弹

12 self.hero.bullets.update()

13 self.hero.bullets.draw(self.screen)

View Code

4.4 显示

1 pygame.display.update()

5、启动与结束游戏

<code> 1 class PlaneGame(object): 2 ...

3 @staticmethod

4 def \_\_game\_over():

5 print("游戏结束")

6

7 pygame.quit()

8 exit()

9

10 if \_\_name\_\_ == '\_\_main\_\_':

11 #创建游戏对象

12 game = PlaneGame()

13 #启动游戏

14 game.start\_game()

View Code

6、游戏优化

本程序所实现的游戏还较为粗糙,可以继续优化。其方向包括但不限于:增加音效,增加飞机爆炸画面,击杀敌机增加积分模式等等。

本文转自 https://www.cnblogs.com/chenmenghu/p/12266046.html,如有侵权,请联系删除。



声明

本文内容仅代表作者观点,或转载于其他网站,本站不以此文作为商业用途
如有涉及侵权,请联系本站进行删除
转载本站原创文章,请注明来源及作者。