import pgzrun import random from pgzhelper import * # 游戏常量配置 WIDTH = 400 # 游戏窗口宽度 HEIGHT = 700 # 游戏窗口高度 TITLE = '逃离地心引力' # 游戏窗口标题 speed = 5 gap = 120 # 平台垂直间距 g = 0.8 # 重力加速度 jump = -15 # 跳跃力(负值表示向上) # 初始化游戏状态 def start(): global plats, p, score, game_over p = Actor("player", (WIDTH // 2, HEIGHT - 70)) # 初始位置底部 plats = [] # 清空平台列表 p.vy = 0 # 垂直速度重置为0 score = 0 # 分数重置为0 game_over = False # 游戏状态重置为未结束 # 生成底部固定平台(屏幕底部中央) base = Actor("platform", (WIDTH // 2, HEIGHT - 30)) plats.append(base) # 生成初始5个平台(从底部向上固定间距随机分布) for i in range(5): x = random.randint(75, WIDTH - 75) # 平台水平位置随机 y = base.y - (gap * (i + 1)) # 平台垂直位置按间距计算 plats.append(Actor("platform", (x, y))) def draw(): screen.blit("starbg.png", (0, 0)) # 绘制背景 # 绘制所有平台 for plat in plats: plat.draw() p.draw() # 绘制玩家 # 显示分数和结束提示 screen.draw.text(f"分数: {score}", (40, 50), color="white", fontname='simkai', fontsize=24) if game_over: screen.draw.text("游戏结束!按 R 重新开始", center=(WIDTH // 2, HEIGHT // 2 - 40), color="white", fontname='simkai', fontsize=24, background="black") def update(): global score, game_over # 游戏结束状态处理(按R键重新开始) if game_over: if keyboard.r: start() # 玩家移动(左右键) p.x += (keyboard.right - keyboard.left) * speed # 边界限制(确保玩家不超出屏幕左右边界) p.x = max(p.width // 2, min(p.x, WIDTH - p.width // 2)) # 物理系统:应用重力(垂直速度递增) p.vy += g p.y += p.vy # 平台碰撞检测(仅当玩家下落时触发) if p.vy > 0: # 像素级碰撞检测(返回碰撞的平台索引,-1表示无碰撞) hit = p.collidelist_pixel(plats) if hit != -1: # 修正玩家位置到平台上方,避免穿模 p.bottom = plats[hit].y - 10 p.vy = jump # 跳跃 sounds.跳1.play() # 跳跃音效 # 屏幕滚动逻辑(玩家上升到中部时下移平台) if p.y < HEIGHT // 2: dis = HEIGHT // 2 - p.y # 计算需要滚动的距离 p.y += dis # 玩家回到屏幕中部 # 所有平台下移 for plat in plats: plat.y += dis # 生成新平台(当顶部平台进入屏幕时,在其上方生成新平台) if plats[-1].y > 0: x = random.randint(75, WIDTH - 75) y = plats[-1].y - gap new = Actor("platform", (x, y)) plats.append(new) # 移除屏幕下方的平台(保留最小数量) while len(plats) > 7: # 限制平台总数 plats.pop(0) score += 10 # 得分 # 游戏结束条件(玩家掉落底部平台之外) if p.y > HEIGHT + p.height: game_over = True start() # 初始化游戏 pgzrun.go() # 运行Pygame Zero游戏循环