Skip to content

Commit 3e6836d

Browse files
committed
【项目实战演练】外星人入侵
1. 增加外星人和飞船碰撞实现 2. 增加死亡后重置(游戏状态机) 3. 修改飞船运行速度和方向为随机
1 parent 433c575 commit 3e6836d

6 files changed

Lines changed: 124 additions & 32 deletions

File tree

alien.png

2.42 KB
Loading

alien.py

Lines changed: 30 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33

44
import pygame
55
from pygame.sprite import Sprite
6+
import random as Random
67

78

89
class Alien(Sprite):
@@ -32,16 +33,20 @@ def __init__(self, screen):
3233
self.__x = float(self.rect.x)
3334
self.__y = float(self.rect.y)
3435

35-
self.__fleet_direction = 'left'
36+
direction_temp = Random.randint(0, 1)
37+
if 0 == direction_temp:
38+
self.__fleet_direction = 'left'
39+
else :
40+
self.__fleet_direction = 'right'
3641
self.__speed = 1
3742
self.__min_distance_alien = 50
3843
self.__min_distance_wall = 40
39-
self.__current_distance_alien_left = 0
40-
self.__current_distance_alien_right = 0
41-
self.__current_distance_wall_left = 0
42-
self.__current_distance_wall_right = 0
43-
self.__current_distance_bottom = 0
44-
self.__current_distance_top = 0
44+
self.__current_distance_alien_left = -1
45+
self.__current_distance_alien_right = -1
46+
self.__current_distance_wall_left = -1
47+
self.__current_distance_wall_right = -1
48+
self.__current_distance_bottom = -1
49+
self.__current_distance_top = -1
4550

4651
def blitme(self):
4752
"""在指定的位置绘制外星人"""
@@ -52,6 +57,7 @@ def update(self):
5257
# self.__x = self.__rect.x
5358
# self.__y = self.__rect.y
5459
# self.__center = self.__rect.centerx
60+
5561
if (self.rect.x + self.rect.width) >= self.__scrren_right:
5662
self.__fleet_direction = 'left'
5763
elif self.rect.x <= self.__scrren_left:
@@ -65,6 +71,11 @@ def update(self):
6571
self.__y += self.__speed
6672
self.rect.y = self.__y
6773
self.rect.x = self.__x
74+
self.__current_distance_wall_left = self.__x - self.__scrren_left
75+
self.__current_distance_wall_right = self.__scrren_right - self.__x - self.rect.width
76+
self.__current_distance_bottom = self.__x - self.__scrren_botoom
77+
self.__current_distance_top = self.__scrren_top - self.__y - self.rect.height
78+
6879

6980
def moving(self):
7081
"""移动外星人"""
@@ -121,6 +132,18 @@ def get_distance_alien(self):
121132
def get_distance_wall(self):
122133
return self.__min_distance_wall
123134

135+
def get_distance_wall_left(self):
136+
return self.__current_distance_wall_left
137+
138+
def get_distance_wall_right(self):
139+
return self.__current_distance_alien_right
140+
141+
def get_distance_wall_bottom(self):
142+
return self.__current_distance_bottom
143+
144+
def get_distance_wall_top(self):
145+
return self.__current_distance_top
146+
124147

125148

126149

alien_invasion.py

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33

44
# import sys
55
import pygame
6-
from settings import Settings
6+
from settings import *
77
from ship import Ship
88
# from alien import Alien
99
import game_functions as gf
@@ -17,6 +17,8 @@ def run_game():
1717
pygame.init()
1818

1919
ai_settings = Settings()
20+
game_state = GameState(ai_settings)
21+
game_state.game_state = 'running'
2022
scrren = pygame.display.set_mode((ai_settings.scrren_width, ai_settings.scrren_height))
2123
pygame.display.set_caption("Alien Invasion")
2224

@@ -27,7 +29,7 @@ def run_game():
2729
# 创建外星人
2830
aliens = Group()
2931
alien_num = ai_settings.cal_alien_num_line_default(scrren)
30-
gf.creat_fleet_alien(scrren, aliens, alien_num)
32+
gf.creat_fleet_alien(scrren, game_state, aliens, alien_num)
3133
ai_settings.set_alien_info_default(aliens, alien_num)
3234

3335
# 开始游戏的主循环
@@ -42,9 +44,12 @@ def run_game():
4244
aliens.update()
4345

4446
# 3.命中外星人处理
45-
gf.alien_short(scrren, aliens, ship, ai_settings)
47+
gf.alien_short(scrren, game_state, aliens, ship, ai_settings)
4648

47-
# 4.重绘屏幕
49+
# 4.外星人过线和飞船碰撞处理
50+
gf.shiphit_alienoverline(scrren, game_state, ship, aliens)
51+
52+
# 5.重绘屏幕
4853
gf.redraw_scrren(ai_settings.bg_color, scrren, ship, aliens)
4954

5055
# time.sleep(1)

game_functions.py

Lines changed: 37 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
import bullet as BULLET
66
from bullet import *
77
from alien import *
8+
from time import sleep
89

910
def check_keyup_event(event, ship):
1011
"""按键释放事件响应"""
@@ -78,19 +79,19 @@ def redraw_scrren(bg_color, scrren, ship, aliens):
7879
pygame.display.flip()
7980

8081

81-
def creat_fleet_alien(screen, aliens, aliens_num):
82+
def creat_fleet_alien(screen, game_state, aliens, aliens_num):
8283
"""创建一群外星人"""
8384
for row in range(aliens_num['row_num']):
8485
for alien in range(aliens_num['list_num']):
8586
alien = Alien(screen)
8687
aliens.add(alien)
8788

8889

89-
def alien_short(scrren, aliens, ship, ai_settings):
90+
def alien_short(scrren, gamge_state, aliens, ship, ai_settings):
9091
"""判断子弹是否命中外星人"""
9192
bullets = ship.get_bullets()
9293
# 求子弹和外星人交集
93-
collisions = pygame.sprite.groupcollide(aliens, bullets, True, False)
94+
collisions = pygame.sprite.groupcollide(aliens, bullets, True, True)
9495

9596
# 外星人都被消灭时重新创建外星人
9697
if 0 == len(aliens):
@@ -99,3 +100,36 @@ def alien_short(scrren, aliens, ship, ai_settings):
99100
creat_fleet_alien(scrren, aliens, alien_num)
100101
ai_settings.set_alien_info_default(aliens, alien_num)
101102
# print collisions
103+
104+
105+
def shiphit_alienoverline(scrren, game_state, ship, aliens):
106+
"""外星人和飞船碰撞和过线处理"""
107+
108+
# for alien in aliens:
109+
# # 任意一个外星人过线
110+
# if 0 == alien.get_distance_wall_top():
111+
# game_state.game_state = 'stop'
112+
113+
if pygame.sprite.spritecollideany(ship, aliens):
114+
game_state.game_state = 'stop'
115+
116+
if 'stop' == game_state.game_state:
117+
if 0 == game_state.ships_left:
118+
game_state.game_active = False
119+
if game_state.game_active is True:
120+
bullets = ship.get_bullets()
121+
bullets.empty()
122+
aliens.empty()
123+
sleep(5)
124+
game_state.ships_left -= 1
125+
aliens_num = game_state.ai_settings.cal_alien_num_line_default(scrren)
126+
creat_fleet_alien(scrren, game_state, aliens, aliens_num)
127+
game_state.ai_settings.set_alien_info_default(aliens, aliens_num)
128+
ship.center_ship()
129+
game_state.game_state = 'running'
130+
131+
else:
132+
sleep(5)
133+
sys.exit()
134+
135+

settings.py

Lines changed: 36 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
# coding: utf-8
22
import ship as SHIP
33
import bullet as BULLET
4-
4+
import random as Random
55

66
class Settings():
77
"""存储《外星人入侵》的所有设置的类"""
@@ -12,24 +12,26 @@ def __init__(self):
1212
# 屏幕设置
1313
self.scrren_width = 650
1414
self.scrren_height = 1000
15-
self.bg_color = (230, 230, 230)
15+
self.bg_color = (255, 255, 255)
1616

1717
# 飞船设置
1818
self.ship_speed = 1
1919
self.ship_bullet_allowed = 100
20+
self.ship_limit = 3
2021

2122
# 子弹设置
22-
self.bullet_speed = 1
23+
self.bullet_speed = 5
2324
self.bullet_width = 3
24-
self.bullet_height = 10
25+
self.bullet_height = 8
2526
self.bullet_color = 0, 0, 0
2627

2728
# 外星人设置
28-
self.alien_speed = 0.05
29+
self.alien_speed_range = {'low': 0.05, 'high': 0.3}
30+
2931
self.alien_max_num = 10
30-
#
31-
self.alien_width = 60
32-
self.alien_height = 60
32+
33+
self.alien_width = 40
34+
self.alien_height = 40
3335
self.alien_min_distance_list = 10
3436
self.alien_min_distance_row = 10
3537
self.alien_min_distance_wall = 10
@@ -96,10 +98,35 @@ def set_alien_info_default(self, aliens, alien_num):
9698
rect.y = self.alien_min_distance_bottom + (row_num - 1) * (alien_height + self.alien_min_distance_row)
9799
rect.x = self.alien_min_distance_wall + (list_num - 1) * (alien_width + self.alien_min_distance_list)
98100
alien.set_rect(rect)
99-
alien.set_speed(self.alien_speed)
101+
alien_speed_set = Random.random()
102+
while (alien_speed_set > self.alien_speed_range['high']) \
103+
or (alien_speed_set < self.alien_speed_range['low']):
104+
alien_speed_set = Random.random()
105+
106+
alien.set_speed(alien_speed_set)
100107
list_num += 1
101108
if list_num > alien_num['list_num']:
102109
list_num = 1
103110
row_num += 1
104111

105112
return True
113+
114+
115+
class GameState():
116+
"""游戏状态数据"""
117+
118+
def __init__(self, ai_settings):
119+
"""初始化统计和状态信息"""
120+
self.ai_settings = ai_settings
121+
self.reset_stats()
122+
self.game_state = 'running'
123+
self.game_active = True
124+
125+
def reset_stats(self):
126+
"""初始化在游戏裕兴期间可能变化的统计信息"""
127+
self.ships_left = self.ai_settings.ship_limit
128+
129+
130+
131+
132+

ship.py

Lines changed: 12 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ def __init__(self, scrren):
1818
# self.__image = pygame.image.load(image_name_ex)
1919
# ship_file_object.close()
2020
self.__image = pygame.image.load_extended('ship.png')
21-
self.__rect = self.__image.get_rect()
21+
self.rect = self.__image.get_rect()
2222
self.__scrren_rect = scrren.get_rect()
2323

2424
# 持续移动标志
@@ -27,9 +27,9 @@ def __init__(self, scrren):
2727
self.__speed_factor = 1
2828

2929
# 将每艘飞船防止在屏幕底部中央
30-
self.__rect.centerx = (self.__scrren_rect.right + self.__scrren_rect.left) / 2
31-
self.__rect.bottom = self.__scrren_rect.bottom
32-
self.__self_center = self.__rect.centerx
30+
self.rect.centerx = (self.__scrren_rect.right + self.__scrren_rect.left) / 2
31+
self.rect.bottom = self.__scrren_rect.bottom
32+
self.__self_center = self.rect.centerx
3333

3434
# 设置对应的子弹
3535
self.__bullet_speed = 1
@@ -42,17 +42,17 @@ def __init__(self, scrren):
4242

4343
def blitme(self):
4444
"""在指定位置放置飞船"""
45-
self.__scrren.blit(self.__image, self.__rect)
45+
self.__scrren.blit(self.__image, self.rect)
4646

4747
def update(self):
4848
"""根据移动标志调整飞船的位置"""
49-
if (True is self.__moving_riht) and self.__rect.right < self.__scrren_rect.right:
49+
if (True is self.__moving_riht) and self.rect.right < self.__scrren_rect.right:
5050
self.__self_center += self.__speed_factor
5151

52-
if (True is self.__moving_left) and self.__rect.left > self.__scrren_rect.left:
52+
if (True is self.__moving_left) and self.rect.left > self.__scrren_rect.left:
5353
self.__self_center -= self.__speed_factor
5454

55-
self.__rect.centerx = self.__self_center
55+
self.rect.centerx = self.__self_center
5656

5757
def moving(self, direction):
5858
"""移动飞船"""
@@ -62,6 +62,9 @@ def moving(self, direction):
6262
self.__moving_riht = True
6363
self.update()
6464

65+
def center_ship(self):
66+
self.__self_center = self.__scrren_rect.centerx
67+
6568
def stop(self):
6669
"""停止移动,将移动标志位都设置为FALSE"""
6770
self.__moving_left = False
@@ -75,7 +78,7 @@ def get_scrren(self):
7578
return self.__scrren
7679

7780
def get_rect(self):
78-
return self.__rect
81+
return self.rect
7982

8083
def get_self_center(self):
8184
return self.__self_center

0 commit comments

Comments
 (0)