销毁并重新启动PyGame对象时出现display Surface quit错误
解决PyGame窗口重复打开后退出时的
pygame.error: display Surface quit错误 我之前也碰到过一模一样的问题——明明功能跑起来都正常,结果退出脚本的时候突然蹦出一堆报错,看着特别闹心。其实这根源是PyGame的display模块在窗口关闭后,没有被彻底重置干净,导致后续重新初始化窗口后,退出时残留的资源状态发生了冲突。
问题根源拆解
当你第一次关闭PyGame窗口时,PyGame会把底层的display Surface标记为"已退出"状态,但如果只是简单结束Game实例,没有彻底清理display相关的资源,下次调用launch_game()重新创建窗口时,虽然表面能正常运行,但底层的display状态其实已经有残留了。等到整个父脚本退出时,这些残留的状态就会触发那个烦人的错误。
可行解决方案
方案1:每次关闭窗口后彻底清理PyGame资源
在你的Game类里加一个清理方法,专门处理display和PyGame的退出逻辑,确保每次窗口关闭后都把资源清干净:
# game.py 中的Game类 import pygame class Game: def __init__(self): pygame.init() self.screen = pygame.display.set_mode((800, 600)) # 其他初始化逻辑 def run(self): # 游戏主循环逻辑 running = True while running: for event in pygame.event.get(): if event.type == pygame.QUIT: running = False # 循环结束后调用清理 self.cleanup() def cleanup(self): pygame.display.quit() # 先关闭display模块 pygame.quit() # 再完全退出PyGame
然后在父脚本里调用时,确保游戏结束后触发清理:
# parent.py from game import Game def launch_game(): game = Game() game.run() # 直到窗口关闭,自动执行cleanup # 第一次启动 launch_game() # 后续再次启动 launch_game()
方案2:全局复用PyGame初始化,只重置窗口
如果不需要每次都完全退出PyGame,可以把初始化放到父脚本的全局范围,每次重新打开窗口时只重置Surface,不销毁整个display模块:
# parent.py 全局初始化 import pygame pygame.init() from game import Game def launch_game(): game = Game() game.run() # Game类里的run方法调整 # game.py class Game: def __init__(self): self.screen = pygame.display.set_mode((800, 600)) def run(self): running = True while running: for event in pygame.event.get(): if event.type == pygame.QUIT: running = False # 关闭窗口但不退出PyGame pygame.display.set_mode((0, 0), pygame.HIDDEN)
这种方式适合需要频繁重启窗口的场景,避免重复初始化PyGame的开销。
方案3:临时捕获特定错误(治标不治本)
如果不想大改代码,也可以在父脚本的主入口捕获这个特定错误,避免报错信息干扰:
# parent.py from game import Game import pygame def launch_game(): game = Game() game.run() if __name__ == "__main__": try: launch_game() launch_game() # 再次启动 except pygame.error as e: # 只忽略display Surface quit的错误,其他错误正常抛出 if "display Surface quit" not in str(e): raise e
不过这个只是临时 workaround,还是推荐前面两种从根源解决的方案。
内容的提问来源于stack exchange,提问作者Frank Bonham
相关产品推荐
相关产品推荐

