Pygame开发游戏详细流程记录

Written by

in

文章目录
  • 游戏主循环 ├── 事件处理 (Event Handling) ├── 游戏逻辑更新 (Game Logic) ├── 渲染绘制 (Rendering) └── 帧率控制 (FPS Control)
  • 显示帧率 fps_text = font.render(f”FPS: {int(clock.get_fps())}”, True, WHITE) 显示调试信息 def draw_debug_info(): debug_info = [ f”玩家位置: ({player.rect.x}, {player.rect.y})”, f”速度: ({player.velocity.x:.1f}, {player.velocity.y:.1f})”, f”金币数量: {len(coins)}”, f”敌人数量: {len(enemies)}” ] for i, info in enumerate(debug_info): text = font.render(info, True, WHITE) screen.blit(text, (10, 30 + i * 25)) 碰撞框显示 pygame.draw.rect(screen, (255, 0, 0), object.rect, 2) # 红色边框
  • my_game/ ├── main.py # 游戏主入口 ├── game.py # 游戏主类 ├── player.py # 玩家类 ├── enemy.py # 敌人类 ├── platform.py # 平台类 ├── powerup.py # 道具类 ├── scene/ │ ├── menu_scene.py # 菜单场景 │ ├── game_scene.py # 游戏场景 │ └── game_over_scene.py ├── assets/ │ ├── images/ │ ├── sounds/ │ └── fonts/ ├── config.py # 配置文件 └── utils.py # 工具函数 按照这个流程,你可以从简单到复杂逐步开发完整的Pygame游戏。记住:先实现核心玩法,再添加特效和优化!
  • 到此这篇关于Pygame开发游戏详细流程记录的文章就介绍到这了,更多相关Pygame开发游戏内容请搜索风君子博客以前的文章或继续浏览下面的相关文章希望大家以后多多支持风君子博客! 您可能感兴趣的文章: 使用python+pygame开发消消乐游戏附完整源码 pygame实现雷电游戏雏形开发 Pygame游戏开发之太空射击实战子弹与碰撞处理篇 Pygame游戏开发实例讲解之图形绘制与键鼠事件 Pygame游戏开发之太空射击实战入门篇 Pygame游戏开发之太空射击实战敌人精灵篇
  • 目录
    • 一、Pygame 核心架构
    • 二、完整开发流程详解
      • 1.基础框架搭建
      • 2.主游戏循环
      • 3.精灵系统(Sprite System)
      • 4.游戏场景管理
      • 5.完整游戏示例:平台跳跃游戏
    • 三、最佳实践和优化技巧
      • 1.性能优化
      • 2.状态机管理
      • 3.粒子系统
    • 四、调试技巧
      • 五、项目结构建议
        • 总结

          游戏主循环
              ├── 事件处理 (Event Handling)
              ├── 游戏逻辑更新 (Game Logic)
              ├── 渲染绘制 (Rendering)
              └── 帧率控制 (FPS Control)
          

          import pygame
          import sys
          
          class Game:
              def __init__(self):
                  """初始化游戏"""
                  pygame.init()
                  
                  # 1. 创建游戏窗口
                  self.screen_width = 800
                  self.screen_height = 600
                  self.screen = pygame.display.set_mode(
                      (self.screen_width, self.screen_height)
                  )
                  pygame.display.set_caption("我的游戏")
                  
                  # 2. 初始化游戏时钟(控制帧率)
                  self.clock = pygame.time.Clock()
                  self.FPS = 60
                  
                  # 3. 游戏状态
                  self.running = True
                  self.game_over = False
                  
                  # 4. 颜色定义(RGB)
                  self.BLACK = (0, 0, 0)
                  self.WHITE = (255, 255, 255)
                  self.RED = (255, 0, 0)
                  self.GREEN = (0, 255, 0)
                  self.BLUE = (0, 0, 255)
                  
                  # 5. 初始化游戏资源
                  self.load_resources()
                  
              def load_resources(self):
                  """加载游戏资源"""
                  # 字体
                  self.font_small = pygame.font.SysFont(None, 36)
                  self.font_large = pygame.font.SysFont(None, 72)
                  
                  # 加载图片
                  try:
                      self.player_image = pygame.image.load("player.png").convert_alpha()
                  except:
                      # 如果图片不存在,创建一个矩形代替
                      self.player_image = pygame.Surface((50, 50))
                      self.player_image.fill(self.BLUE)
                  
                  # 加载音效
                  try:
                      self.jump_sound = pygame.mixer.Sound("jump.wav")
                  except:
                      self.jump_sound = None
                      
                  # 背景音乐
                  pygame.mixer.music.load("bgm.mp3")
                  pygame.mixer.music.play(-1)  # -1表示循环播放
          

              def run(self):
                  """主游戏循环"""
                  while self.running:
                      # 1. 处理事件
                      self.handle_events()
                      
                      # 2. 更新游戏状态(只有游戏没结束时才更新)
                      if not self.game_over:
                          self.update()
                      
                      # 3. 绘制画面
                      self.render()
                      
                      # 4. 控制帧率
                      self.clock.tick(self.FPS)
                      
                  # 游戏结束,退出
                  self.quit()
              
              def handle_events(self):
                  """事件处理"""
                  for event in pygame.event.get():
                      if event.type == pygame.QUIT:
                          self.running = False
                          
                      # 键盘按下事件
                      elif event.type == pygame.KEYDOWN:
                          self.on_key_down(event.key)
                          
                      # 键盘释放事件
                      elif event.type == pygame.KEYUP:
                          self.on_key_up(event.key)
                          
                      # 鼠标事件
                      elif event.type == pygame.MOUSEBUTTONDOWN:
                          self.on_mouse_click(event.pos, event.button)
          

          class Player(pygame.sprite.Sprite):
              """玩家角色类"""
              def __init__(self, x, y):
                  super().__init__()
                  
                  # 创建图像和矩形
                  self.image = pygame.Surface((50, 50))
                  self.image.fill((0, 0, 255))
                  
                  # 加载动画帧
                  self.frames = []
                  self.load_animation_frames()
                  self.current_frame = 0
                  self.animation_speed = 0.2
                  self.animation_timer = 0
                  
                  self.rect = self.image.get_rect()
                  self.rect.center = (x, y)
                  
                  # 物理属性
                  self.velocity = pygame.Vector2(0, 0)
                  self.speed = 5
                  self.jump_power = -15
                  self.gravity = 0.8
                  self.on_ground = False
                  
                  # 游戏属性
                  self.health = 100
                  self.score = 0
                  
              def load_animation_frames(self):
                  """加载动画帧"""
                  for i in range(4):
                      frame = pygame.Surface((50, 50))
                      frame.fill((0, 0, 200 + i * 15))
                      self.frames.append(frame)
              
              def update(self, platforms):
                  """更新玩家状态"""
                  # 处理用户输入
                  keys = pygame.key.get_pressed()
                  
                  # 水平移动
                  self.velocity.x = 0
                  if keys[pygame.K_LEFT]:
                      self.velocity.x = -self.speed
                  if keys[pygame.K_RIGHT]:
                      self.velocity.x = self.speed
                      
                  # 跳跃
                  if keys[pygame.K_SPACE] and self.on_ground:
                      self.velocity.y = self.jump_power
                      self.on_ground = False
                      
                  # 应用重力
                  self.velocity.y += self.gravity
                  
                  # 水平移动
                  self.rect.x += self.velocity.x
                  
                  # 水平碰撞检测
                  self.check_horizontal_collision(platforms)
                  
                  # 垂直移动
                  self.rect.y += self.velocity.y
                  
                  # 垂直碰撞检测
                  self.check_vertical_collision(platforms)
                  
                  # 更新动画
                  self.update_animation()
                  
                  # 边界检查
                  self.check_bounds()
              
              def check_horizontal_collision(self, platforms):
                  for platform in platforms:
                      if self.rect.colliderect(platform):
                          if self.velocity.x > 0:  # 向右移动
                              self.rect.right = platform.left
                          elif self.velocity.x < 0:  # 向左移动
                              self.rect.left = platform.right
              
              def check_vertical_collision(self, platforms):
                  self.on_ground = False
                  for platform in platforms:
                      if self.rect.colliderect(platform):
                          if self.velocity.y > 0:  # 向下移动
                              self.rect.bottom = platform.top
                              self.velocity.y = 0
                              self.on_ground = True
                          elif self.velocity.y < 0:  # 向上移动
                              self.rect.top = platform.bottom
                              self.velocity.y = 0
              
              def update_animation(self):
                  """更新动画帧"""
                  self.animation_timer += self.animation_speed
                  if self.animation_timer >= 1:
                      self.current_frame = (self.current_frame + 1) % len(self.frames)
                      self.image = self.frames[self.current_frame]
                      self.animation_timer = 0
              
              def check_bounds(self):
                  """检查边界"""
                  if self.rect.top > 600:  # 掉落屏幕
                      self.health = 0
          

          class GameScene:
              """游戏场景基类"""
              def __init__(self, game):
                  self.game = game
                  
              def handle_events(self):
                  pass
              
              def update(self):
                  pass
              
              def render(self):
                  pass
          
          class MainMenuScene(GameScene):
              """主菜单场景"""
              def __init__(self, game):
                  super().__init__(game)
                  self.buttons = []
                  self.create_buttons()
              
              def create_buttons(self):
                  """创建菜单按钮"""
                  button_width, button_height = 200, 50
                  
                  # 开始游戏按钮
                  start_rect = pygame.Rect(
                      self.game.screen_width // 2 - button_width // 2,
                      200,
                      button_width,
                      button_height
                  )
                  self.buttons.append({
                      'rect': start_rect,
                      'text': '开始游戏',
                      'action': self.start_game
                  })
                  
                  # 退出游戏按钮
                  quit_rect = pygame.Rect(
                      self.game.screen_width // 2 - button_width // 2,
                      280,
                      button_width,
                      button_height
                  )
                  self.buttons.append({
                      'rect': quit_rect,
                      'text': '退出游戏',
                      'action': self.quit_game
                  })
              
              def handle_events(self):
                  for event in pygame.event.get():
                      if event.type == pygame.QUIT:
                          self.game.running = False
                      elif event.type == pygame.MOUSEBUTTONDOWN:
                          if event.button == 1:  # 左键
                              self.check_button_click(event.pos)
              
              def check_button_click(self, pos):
                  """检查按钮点击"""
                  for button in self.buttons:
                      if button['rect'].collidepoint(pos):
                          button['action']()
              
              def start_game(self):
                  """切换到游戏场景"""
                  self.game.current_scene = GamePlayScene(self.game)
              
              def quit_game(self):
                  self.game.running = False
              
              def render(self):
                  # 绘制背景
                  self.game.screen.fill((30, 30, 70))
                  
                  # 绘制标题
                  title_font = pygame.font.SysFont(None, 72)
                  title_text = title_font.render("我的游戏", True, (255, 255, 255))
                  title_rect = title_text.get_rect(center=(self.game.screen_width//2, 100))
                  self.game.screen.blit(title_text, title_rect)
                  
                  # 绘制按钮
                  for button in self.buttons:
                      # 绘制按钮背景
                      pygame.draw.rect(self.game.screen, (50, 150, 200), button['rect'])
                      pygame.draw.rect(self.game.screen, (255, 255, 255), button['rect'], 3)
                      
                      # 绘制按钮文字
                      button_font = pygame.font.SysFont(None, 36)
                      button_text = button_font.render(button['text'], True, (255, 255, 255))
                      text_rect = button_text.get_rect(center=button['rect'].center)
                      self.game.screen.blit(button_text, text_rect)
          

          import pygame
          import sys
          import random
          
          class PlatformGame:
              def __init__(self):
                  pygame.init()
                  
                  # 屏幕设置
                  self.WIDTH = 800
                  self.HEIGHT = 600
                  self.screen = pygame.display.set_mode((self.WIDTH, self.HEIGHT))
                  pygame.display.set_caption("平台跳跃")
                  
                  # 颜色
                  self.SKY_BLUE = (135, 206, 235)
                  self.GROUND_COLOR = (101, 67, 33)
                  self.PLATFORM_COLOR = (0, 200, 100)
                  
                  # 游戏状态
                  self.clock = pygame.time.Clock()
                  self.FPS = 60
                  self.running = True
                  self.score = 0
                  self.font = pygame.font.SysFont(None, 36)
                  
                  # 游戏对象
                  self.player = pygame.Rect(100, 300, 30, 30)
                  self.player_vel_y = 0
                  self.gravity = 0.8
                  self.jump_strength = -15
                  self.on_ground = False
                  
                  # 平台
                  self.platforms = [
                      pygame.Rect(0, 500, 800, 100),  # 地面
                      pygame.Rect(200, 400, 200, 20),
                      pygame.Rect(450, 350, 150, 20),
                      pygame.Rect(300, 250, 200, 20),
                      pygame.Rect(100, 200, 150, 20),
                      pygame.Rect(550, 150, 200, 20),
                  ]
                  
                  # 金币
                  self.coins = []
                  self.generate_coins()
                  
                  # 敌人
                  self.enemies = []
                  self.spawn_timer = 0
                  self.spawn_interval = 2000  # 毫秒
                  
              def generate_coins(self):
                  """生成金币"""
                  for platform in self.platforms[1:]:  # 除了地面
                      x = random.randint(platform.left + 10, platform.right - 20)
                      y = platform.top - 30
                      self.coins.append(pygame.Rect(x, y, 15, 15))
              
              def handle_events(self):
                  for event in pygame.event.get():
                      if event.type == pygame.QUIT:
                          self.running = False
                      elif event.type == pygame.KEYDOWN:
                          if event.key == pygame.K_SPACE and self.on_ground:
                              self.player_vel_y = self.jump_strength
                              self.on_ground = False
                          elif event.key == pygame.K_r:  # 重新开始
                              self.__init__()
              
              def update(self):
                  # 键盘输入
                  keys = pygame.key.get_pressed()
                  
                  # 水平移动
                  player_speed = 5
                  if keys[pygame.K_LEFT]:
                      self.player.x -= player_speed
                  if keys[pygame.K_RIGHT]:
                      self.player.x += player_speed
                      
                  # 应用重力
                  self.player_vel_y += self.gravity
                  self.player.y += self.player_vel_y
                  
                  # 边界检查
                  if self.player.left < 0:
                      self.player.left = 0
                  if self.player.right > self.WIDTH:
                      self.player.right = self.WIDTH
                      
                  # 平台碰撞检测
                  self.on_ground = False
                  for platform in self.platforms:
                      if self.player.colliderect(platform):
                          if self.player_vel_y > 0:  # 下落
                              self.player.bottom = platform.top
                              self.player_vel_y = 0
                              self.on_ground = True
                          elif self.player_vel_y < 0:  # 上升
                              self.player.top = platform.bottom
                              self.player_vel_y = 0
                  
                  # 金币收集
                  for coin in self.coins[:]:
                      if self.player.colliderect(coin):
                          self.coins.remove(coin)
                          self.score += 10
                  
                  # 生成敌人
                  current_time = pygame.time.get_ticks()
                  if current_time - self.spawn_timer > self.spawn_interval:
                      self.enemies.append(pygame.Rect(
                          random.randint(0, self.WIDTH - 30),
                          -30,
                          30, 30
                      ))
                      self.spawn_timer = current_time
                  
                  # 更新敌人
                  for enemy in self.enemies[:]:
                      enemy.y += 3
                      if enemy.top > self.HEIGHT:
                          self.enemies.remove(enemy)
                      
                      # 玩家与敌人碰撞
                      if self.player.colliderect(enemy):
                          self.game_over()
              
              def game_over(self):
                  """游戏结束"""
                  game_over_font = pygame.font.SysFont(None, 72)
                  game_over_text = game_over_font.render("游戏结束!", True, (255, 0, 0))
                  score_text = self.font.render(f"最终得分: {self.score}", True, (255, 255, 255))
                  restart_text = self.font.render("按 R 重新开始", True, (255, 255, 255))
                  
                  # 绘制半透明背景
                  overlay = pygame.Surface((self.WIDTH, self.HEIGHT), pygame.SRCALPHA)
                  overlay.fill((0, 0, 0, 180))
                  self.screen.blit(overlay, (0, 0))
                  
                  # 绘制文字
                  self.screen.blit(game_over_text, 
                                  (self.WIDTH//2 - game_over_text.get_width()//2, 
                                   self.HEIGHT//2 - 100))
                  self.screen.blit(score_text,
                                  (self.WIDTH//2 - score_text.get_width()//2,
                                   self.HEIGHT//2))
                  self.screen.blit(restart_text,
                                  (self.WIDTH//2 - restart_text.get_width()//2,
                                   self.HEIGHT//2 + 50))
                  
                  pygame.display.flip()
                  
                  # 等待玩家按键
                  waiting = True
                  while waiting:
                      for event in pygame.event.get():
                          if event.type == pygame.QUIT:
                              self.running = False
                              waiting = False
                          elif event.type == pygame.KEYDOWN:
                              if event.key == pygame.K_r:
                                  self.__init__()
                                  waiting = False
              
              def render(self):
                  # 绘制背景
                  self.screen.fill(self.SKY_BLUE)
                  
                  # 绘制平台
                  for platform in self.platforms:
                      pygame.draw.rect(self.screen, self.PLATFORM_COLOR, platform)
                  
                  # 绘制地面
                  pygame.draw.rect(self.screen, self.GROUND_COLOR, self.platforms[0])
                  
                  # 绘制金币
                  for coin in self.coins:
                      pygame.draw.circle(self.screen, (255, 215, 0), coin.center, coin.width//2)
                  
                  # 绘制敌人
                  for enemy in self.enemies:
                      pygame.draw.rect(self.screen, (255, 0, 0), enemy)
                  
                  # 绘制玩家
                  pygame.draw.rect(self.screen, (0, 0, 255), self.player)
                  
                  # 绘制分数
                  score_text = self.font.render(f"分数: {self.score}", True, (255, 255, 255))
                  self.screen.blit(score_text, (10, 10))
                  
                  pygame.display.flip()
              
              def run(self):
                  while self.running:
                      self.handle_events()
                      self.update()
                      self.render()
                      self.clock.tick(self.FPS)
                  
                  pygame.quit()
                  sys.exit()
          
          if __name__ == "__main__":
              game = PlatformGame()
              game.run()
          

          # 1. 使用双缓冲
          screen = pygame.display.set_mode((width, height), pygame.DOUBLEBUF)
          
          # 2. 图像转换优化
          image = pygame.image.load("image.png").convert()  # 普通转换
          image = pygame.image.load("image.png").convert_alpha()  # 带透明度转换
          
          # 3. 脏矩形更新(只更新变化的部分)
          dirty_rects = []
          dirty_rects.append(player.rect)
          pygame.display.update(dirty_rects)
          
          # 4. 对象池(减少对象创建销毁)
          class ObjectPool:
              def __init__(self, create_func, max_size=100):
                  self.pool = []
                  self.create_func = create_func
                  self.max_size = max_size
              
              def get(self):
                  if self.pool:
                      return self.pool.pop()
                  return self.create_func()
              
              def recycle(self, obj):
                  if len(self.pool) < self.max_size:
                      self.pool.append(obj)
          

          class StateMachine:
              def __init__(self):
                  self.states = {}
                  self.current_state = None
              
              def add_state(self, name, state):
                  self.states[name] = state
              
              def change_state(self, name):
                  if self.current_state:
                      self.current_state.exit()
                  
                  self.current_state = self.states[name]
                  self.current_state.enter()
              
              def update(self):
                  if self.current_state:
                      self.current_state.update()
              
              def render(self):
                  if self.current_state:
                      self.current_state.render()
          
          class GameState:
              def enter(self):
                  pass
              def exit(self):
                  pass
              def update(self):
                  pass
              def render(self):
                  pass
          

          class Particle:
              def __init__(self, x, y):
                  self.x = x
                  self.y = y
                  self.vx = random.uniform(-2, 2)
                  self.vy = random.uniform(-5, -2)
                  self.lifetime = 60
                  self.color = random.choice([(255, 255, 0), (255, 165, 0)])
              
              def update(self):
                  self.x += self.vx
                  self.y += self.vy
                  self.vy += 0.1
                  self.lifetime -= 1
              
              def draw(self, screen):
                  radius = max(1, self.lifetime // 15)
                  pygame.draw.circle(screen, self.color, (int(self.x), int(self.y)), radius)
          

          1. 显示帧率
          fps_text = font.render(f"FPS: {int(clock.get_fps())}", True, WHITE)
          
          1. 显示调试信息
          def draw_debug_info():
              debug_info = [
                  f"玩家位置: ({player.rect.x}, {player.rect.y})",
                  f"速度: ({player.velocity.x:.1f}, {player.velocity.y:.1f})",
                  f"金币数量: {len(coins)}",
                  f"敌人数量: {len(enemies)}"
              ]
              
              for i, info in enumerate(debug_info):
                  text = font.render(info, True, WHITE)
                  screen.blit(text, (10, 30 + i * 25))
          
          1. 碰撞框显示
          pygame.draw.rect(screen, (255, 0, 0), object.rect, 2)  # 红色边框
          

          my_game/
          ├── main.py              # 游戏主入口
          ├── game.py              # 游戏主类
          ├── player.py            # 玩家类
          ├── enemy.py             # 敌人类
          ├── platform.py          # 平台类
          ├── powerup.py           # 道具类
          ├── scene/
          │   ├── menu_scene.py    # 菜单场景
          │   ├── game_scene.py    # 游戏场景
          │   └── game_over_scene.py
          ├── assets/
          │   ├── images/
          │   ├── sounds/
          │   └── fonts/
          ├── config.py            # 配置文件
          └── utils.py             # 工具函数
          

          按照这个流程,你可以从简单到复杂逐步开发完整的Pygame游戏。记住:先实现核心玩法,再添加特效和优化!

          到此这篇关于Pygame开发游戏详细流程记录的文章就介绍到这了,更多相关Pygame开发游戏内容请搜索风君子博客以前的文章或继续浏览下面的相关文章希望大家以后多多支持风君子博客!

          您可能感兴趣的文章:

          • 使用python+pygame开发消消乐游戏附完整源码
          • pygame实现雷电游戏雏形开发
          • Pygame游戏开发之太空射击实战子弹与碰撞处理篇
          • Pygame游戏开发实例讲解之图形绘制与键鼠事件
          • Pygame游戏开发之太空射击实战入门篇
          • Pygame游戏开发之太空射击实战敌人精灵篇

          站内搜索