You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Pygame开发贪吃蛇时苹果Surface仅在游戏冻结时显示该如何解决

问题原因分析
  • 你在一帧内调用了两次pygame.display.flip()刷新屏幕:先调用apple.spawn()绘制苹果并刷新,此时屏幕上只有苹果;紧接着调用snake.move()最终执行snake.draw(),第一步就用绿色填充了整个画布覆盖了苹果,绘制完蛇后再次刷新,此时用户看到的画面就只有蛇,苹果被覆盖掉了。
  • 只有游戏结束时fps被设为0,snake.draw()不会执行,苹果绘制并刷新后没有后续的覆盖操作,就会停留在屏幕上。fps调高后闪现是因为两次刷新间隔过短,人眼会偶尔捕捉到第一次刷新的苹果画面。
修复方案

调整绘制逻辑,统一每帧的绘制和刷新流程:

  1. 移除Apple.spawn()和Snake.draw()中的pygame.display.flip()调用
  2. 每帧先清空画布,再依次绘制苹果、蛇,最后统一刷新一次屏幕
  3. 移除Snake.draw()中的画布填充操作,放到主循环统一处理
修复后的完整代码
import random
import pygame


class Game:
    def __init__(self):
        pygame.init()
        self.board = pygame.display.set_mode((400, 400))
        self.apple = Apple(self.board)
        self.snake = Snake(self.board, self)
        self.direction = 'right'
        self.going = True
        self.fps = 5

    def play(self):
        clock = pygame.time.Clock()
        while self.going:
            clock.tick(self.fps)
            for event in pygame.event.get():
                if event.type == pygame.QUIT:
                    self.going = False
                if event.type == pygame.KEYDOWN:
                    if event.key == pygame.K_LEFT:
                        self.direction = 'left'
                    if event.key == pygame.K_RIGHT:
                        self.direction = 'right'
                    if event.key == pygame.K_UP:
                        self.direction = 'up'
                    if event.key == pygame.K_DOWN:
                        self.direction = 'down'
            # 统一绘制逻辑
            self.board.fill((0, 255, 0)) # 每帧先清空画布
            self.apple.spawn()
            self.snake.move(self.direction)
            pygame.display.flip() # 全部绘制完成后统一刷新

    def game_over(self):
        self.fps = 0

    def get_fps(self):
        return self.fps


class Snake:
    def __init__(self, board, game):
        self.board = board
        self.image = pygame.Surface((10, 10))
        self.game = game

        self.length = 5
        self.x = [10] * self.length
        self.y = [10] * self.length

    def move(self, direction):
        for i in range(self.length-1, 0, -1):
            self.x[i] = self.x[i-1]
            self.y[i] = self.y[i-1]

        if direction == 'right':
            self.x[0] += 10
        if direction == 'left':
            self.x[0] -= 10
        if direction == 'up':
            self.y[0] -= 10
        if direction == 'down':
            self.y[0] += 10

        if self.x[0] == self.board.get_width() or self.x[0] == -10 or\
                self.y[0] == self.board.get_height() or self.y[0] == -10:
            self.game.game_over()

        if self.game.get_fps() != 0:
            self.draw()

    def draw(self):
        # 移除fill和flip操作
        for i in range(self.length):
            self.board.blit(self.image, (self.x[i], self.y[i]))


class Apple:
    def __init__(self, board):
        self.board = board
        self.image = pygame.Surface((10, 10))
        self.image.fill(pygame.color.Color('red'))
        # 调整随机坐标范围,避免苹果超出屏幕、和蛇网格不对齐
        self.x = random.randint(0, (self.board.get_width()-10)//10)*10
        self.y = random.randint(0, (self.board.get_height()-10)//10)*10

    def spawn(self):
        self.board.blit(self.image, (self.x, self.y))
        # 移除flip操作


if __name__ == '__main__':
    game = Game()
    game.play()

内容的提问来源于stack exchange,提问作者Uponn

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.28 22:45:09