本文将详细介绍如何用Python编写一个简单的雷电飞机大战小游戏,涉及到的知识点包括:Pygame游戏引擎、游戏循环、事件处理等。

一、准备工作

在开始编写游戏之前,需要安装Pygame游戏引擎。Pygame是一套Python模块,用于开发2D视频游戏。

pip install pygame

安装完成后,我们可以开始编写游戏了。

二、游戏框架

为了更好地组织代码,我们将游戏分为两个主要部分:游戏循环和事件处理。

游戏循环负责更新游戏的状态,并在每个循环中绘制游戏的界面,以及处理用户的输入。

事件处理是在游戏循环中运行的,以响应用户的输入,例如按下键盘、移动鼠标等事件。

三、游戏循环

游戏循环是指负责更新游戏状态和绘制游戏界面的一系列操作。我们将使用pygame.time模块来控制游戏循环。

import pygame

# 初始化Pygame引擎
pygame.init()

# 设置窗口大小
screen_width = 480
screen_height = 640
screen = pygame.display.set_mode((screen_width, screen_height))

# 设置游戏标题
pygame.display.set_caption("雷电飞机大战")

# 游戏循环
clock = pygame.time.Clock()
FPS = 60

while True:
  # 设置游戏帧数
  clock.tick(FPS)
  
  # 更新游戏状态
  update_game_state()
  
  # 绘制游戏界面
  draw_game_screen()
  
  # 处理用户的输入事件
  handle_user_input()
  
  # 刷新屏幕
  pygame.display.update()

四、事件处理

事件处理主要是为了响应用户的输入事件,例如按下键盘、移动鼠标等事件。我们将使用pygame.event模块来处理事件。

import pygame

# 初始化Pygame引擎
pygame.init()

# 设置窗口大小
screen_width = 480
screen_height = 640
screen = pygame.display.set_mode((screen_width, screen_height))

# 设置游戏标题
pygame.display.set_caption("雷电飞机大战")

# 游戏循环
clock = pygame.time.Clock()
FPS = 60

while True:
  # 设置游戏帧数
  clock.tick(FPS)
  
  # 处理事件
  for event in pygame.event.get():
    if event.type == pygame.QUIT:
      pygame.quit()
      sys.exit()
    else:
      handle_game_events(event)
      
  # 更新游戏状态
  update_game_state()
  
  # 绘制游戏界面
  draw_game_screen()
  
  # 刷新屏幕
  pygame.display.update()

五、游戏逻辑

接下来我们将讨论游戏逻辑,包括飞机的移动、子弹的发射、敌机的出现等。

1. 飞机的移动

我们将使用WASD、上下左右箭头键来控制飞机的移动。飞机可以水平或垂直移动,但不能移出屏幕。

# 飞机的初始位置
plane_x = screen_width / 2
plane_y = screen_height - 100

# 飞机的移动速度
plane_speed = 5

def handle_game_events(event):
  global plane_x, plane_y
  
  if event.type == pygame.KEYDOWN:
    if event.key == pygame.K_w or event.key == pygame.K_UP:
      plane_y -= plane_speed
    elif event.key == pygame.K_s or event.key == pygame.K_DOWN:
      plane_y += plane_speed
    elif event.key == pygame.K_a or event.key == pygame.K_LEFT:
      plane_x -= plane_speed
    elif event.key == pygame.K_d or event.key == pygame.K_RIGHT:
      plane_x += plane_speed
      
  # 确保飞机不会移出屏幕
  plane_x = max(0, min(plane_x, screen_width))
  plane_y = max(0, min(plane_y, screen_height))

2. 子弹的发射

我们使用空格键来发射子弹。每个子弹都有一个位置和一个速度。

# 子弹的初始位置
bullet_x = plane_x
bullet_y = plane_y

# 子弹的移动速度
bullet_speed = 10

# 是否发射子弹
is_shooting = False

def handle_game_events(event):
  global is_shooting
  
  if event.type == pygame.KEYDOWN:
    if event.key == pygame.K_SPACE:
      is_shooting = True
  elif event.type == pygame.KEYUP:
    if event.key == pygame.K_SPACE:
      is_shooting = False
      
def update_game_state():
  global bullet_x, bullet_y
  
  # 如果正在发射子弹,则让子弹向上移动
  if is_shooting:
    bullet_y -= bullet_speed
      
  # 如果子弹移出了屏幕,则将其移回到飞机的位置
  if bullet_y <= 0:
    bullet_x = plane_x
    bullet_y = plane_y
      
  # 检测子弹是否击中了敌机
  detect_collision()

def draw_game_screen():
  # 绘制飞机
  pygame.draw.rect(screen, (255, 0 ,0), (plane_x, plane_y, 50, 50))
  
  # 绘制子弹
  if is_shooting:
    pygame.draw.rect(screen, (255, 255, 0), (bullet_x, bullet_y, 10, 10))

def detect_collision():
  # 如果子弹击中了敌机,则将敌机移除,并将得分加1
  pass

3. 敌机的出现

敌机将在屏幕的顶部随机出现,然后沿着竖直方向向下移动,直到移出屏幕。

# 敌机的初始位置和速度
enemy_x = random.randint(0, screen_width - 50)
enemy_y = 0
enemy_speed = 5

# 敌机的大小
enemy_size = (50, 50)

# 敌机是否出现
is_enemy_spawned = False

def update_game_state():
  global enemy_y, is_enemy_spawned
  
  # 更新敌机的位置
  if is_enemy_spawned:
    enemy_y += enemy_speed
  
  # 如果敌机已经移出屏幕,则随机生成一个新的敌机
  if enemy_y > screen_height:
    enemy_x = random.randint(0, screen_width - enemy_size[0])
    enemy_y = -enemy_size[1]
    is_enemy_spawned = True
      
  # 检测敌机和子弹之间的碰撞
  detect_collision()

def draw_game_screen():
  # 绘制敌机
  if is_enemy_spawned:
    pygame.draw.rect(screen, (0, 0, 255), (enemy_x, enemy_y, enemy_size[0], enemy_size[1]))

六、完整代码

import pygame
import random

# 初始化Pygame引擎
pygame.init()

# 设置窗口大小
screen_width = 480
screen_height = 640
screen = pygame.display.set_mode((screen_width, screen_height))

# 设置游戏标题
pygame.display.set_caption("雷电飞机大战")

# 游戏循环
clock = pygame.time.Clock()
FPS = 60

# 飞机的初始位置和速度
plane_x = screen_width / 2
plane_y = screen_height - 100
plane_speed = 5

# 是否发射子弹
is_shooting = False

# 子弹的初始位置和速度
bullet_x = plane_x
bullet_y = plane_y
bullet_speed = 10

# 敌机的初始位置和速度
enemy_x = random.randint(0, screen_width - 50)
enemy_y = 0
enemy_speed = 5

# 敌机的大小
enemy_size = (50, 50)

# 敌机是否出现
is_enemy_spawned = False

def handle_game_events(event):
  global is_shooting
  
  if event.type == pygame.KEYDOWN:
    if event.key == pygame.K_SPACE:
      is_shooting = True
  elif event.type == pygame.KEYUP:
    if event.key == pygame.K_SPACE:
      is_shooting = False

def detect_collision():
  global is_enemy_spawned
  
  # 如果子弹击中了敌机,则将敌机移除,并将得分加1
  if is_enemy_spawned and bullet_y  enemy_x and bullet_x < enemy_x + enemy_size[0]:
      is_enemy_spawned = False

def update_game_state():
  global plane_x, plane_y, bullet_x, bullet_y, enemy_y, is_enemy_spawned
  
  # 如果正在发射子弹,则让子弹向上移动
  if is_shooting:
    bullet_y -= bullet_speed
      
  # 如果子弹移出了屏幕,则将其移回到飞机的位置
  if bullet_y  screen_height:
    enemy_x = random.randint(0, screen_width - enemy_size[0])
    enemy_y = -enemy_size[1]
    is_enemy_spawned = True
      
  # 移动飞机
  keys = pygame.key.get_pressed()
  if keys[pygame.K_w] or keys[pygame.K_UP]:
    plane_y -= plane_speed
  if keys[pygame.K_s] or keys[pygame.K_DOWN]:
    plane_y += plane_speed
  if keys[pygame.K_a] or keys[pygame.K_LEFT]:
    plane_x -= plane_speed
  if keys[pygame.K_d] or keys[pygame.K_RIGHT]:
    plane_x += plane_speed
  
  # 确保飞机不会移出屏幕
  plane_x = max(0, min(plane_x, screen_width))
  plane_y = max(0, min(plane_y, screen_height))
      
  # 检测子弹是否击中了敌机
  detect_collision()

def draw_game_screen():
  # 绘制飞机
  pygame.draw.rect(screen, (255, 0 ,0), (plane_x, plane_y, 50, 50))
  
  # 绘制子弹
  if is_shooting:
    pygame.draw.rect(screen, (255, 255, 0), (bullet_x, bullet_y, 10, 10))
  
  # 绘制敌机
  if is_enemy_spawned:
    pygame.draw.rect(screen, (0, 0, 255), (enemy_x, enemy_y, enemy_size[0], enemy_size[1]))

while True:
  # 设置游戏帧数
  clock.tick(FPS)
  
  # 处理事件
  for event in pygame.event.get():
    if event.type == pygame.QUIT:
      pygame.quit()
      sys.exit()
    else:
      handle_game_events(event)
      
  # 更新游戏状态
  update_game_state()
  
  # 绘制游戏界面
  draw_game_screen()
  
  # 刷新屏幕
  pygame.display.update()