pygame显示闪烁问题
本帖最后由 flyps 于 2024-2-24 22:44 编辑import pygame
import sys
from pygame.locals import *
pygame.init()
size = width, height = 600, 400
bg_colour = (255, 255, 255)
fullscreen = False
modes = pygame.display.list_modes()
clock = pygame.time.Clock()
bg = pygame.image.load("waterfall.jpg")
pygame.display.set_caption("MyUndertale")
bg_position = bg.get_rect()
while True:
for event in pygame.event.get():
if event.type == QUIT:
sys.exit()
if event.type == KEYDOWN:
if event.key == K_F4:
fullscreen = not fullscreen
if fullscreen:
screen = pygame.display.set_mode(modes, FULLSCREEN | HWSURFACE)
else:
screen = pygame.display.set_mode(size)
screen.fill(bg_colour)
screen.blit(bg, bg_position)
pygame.display.flip()
clock.tick(100)
#pygame.time.delay(10)
问为什么程序运行以后会闪烁?在线等,急!{:10_269:} 已经找到闪烁的原因,是在循环中每循环一次都要执行的if fullscreen:
screen = pygame.display.set_mode(modes, FULLSCREEN | HWSURFACE)
else:
screen = pygame.display.set_mode(size)
将这部分代码移到按键判断里去,就能减少这段代码的执行次数
import pygame
import sys
from pygame.locals import *
pygame.init()
size = width, height = 600, 400
bg_colour = (255, 255, 255)
fullscreen = False
modes = pygame.display.list_modes()
clock = pygame.time.Clock()
bg = pygame.image.load("waterfall.jpg")
pygame.display.set_caption("MyUndertale")
bg_position = bg.get_rect()
screen = pygame.display.set_mode(size)
while True:
for event in pygame.event.get():
if event.type == QUIT:
pygame.quit()
sys.exit()
if event.type == KEYDOWN and event.key == K_F4:
fullscreen = not fullscreen
if fullscreen:
screen = pygame.display.set_mode(modes, FULLSCREEN | HWSURFACE)
else:
screen = pygame.display.set_mode(size)
screen.fill(bg_colour)
screen.blit(bg, bg_position)
pygame.display.flip() 闪烁问题可能是由于两个原因导致的,一个是更新屏幕时屏幕被清空以及重新绘制,另一个是程序运行速度过快。
首先,我们来解决屏幕被清空和重新绘制的问题。在你的代码中,每次循环开始时,你都使用`screen.fill(bg_colour)`来填充整个屏幕,这会导致屏幕上之前绘制的图像被清空。为了避免这种情况,你可以将`screen.fill(bg_colour)`移动到while循环的外面,并且在循环内部只更新你想要绘制的图像。修改后的代码如下:
while True:
for event in pygame.event.get():
if event.type == QUIT:
sys.exit()
if event.type == KEYDOWN:
if event.key == K_F4:
fullscreen = not fullscreen
if fullscreen:
screen = pygame.display.set_mode(modes, FULLSCREEN | HWSURFACE)
else:
screen = pygame.display.set_mode(size)
screen.fill(bg_colour)# 将填充屏幕的操作放到循环外面
screen.blit(bg, bg_position)
pygame.display.flip()
clock.tick(100)
#pygame.time.delay(10)
接下来,我们来解决程序运行速度过快的问题。在你的代码中,你使用了`clock.tick(100)`来限制帧率为100帧/秒,但是这个方法无法保证达到精确的帧率,而且在有些系统上可能会导致闪烁。我建议你使用`pygame.time.delay(10)`来在每一次循环后延迟10毫秒,这样可以降低程序运行速度,减少闪烁的可能性。
修改后的代码如下:
while True:
for event in pygame.event.get():
if event.type == QUIT:
sys.exit()
if event.type == KEYDOWN:
if event.key == K_F4:
fullscreen = not fullscreen
if fullscreen:
screen = pygame.display.set_mode(modes, FULLSCREEN | HWSURFACE)
else:
screen = pygame.display.set_mode(size)
screen.fill(bg_colour)
screen.blit(bg, bg_position)
pygame.display.flip()
# clock.tick(100)# 注释掉这行
pygame.time.delay(10)# 添加延迟
希望以上修改能够解决你的闪烁问题!
以上回复来自 FishC AI 小助理,如未能正确解答您的问题,请继续追问。 FishC 发表于 2024-2-24 22:41
闪烁问题可能是由于两个原因导致的,一个是更新屏幕时屏幕被清空以及重新绘制,另一个是程序运行速度过快。 ...
没用啊,能根据问题一继续修改吗?
flyps 发表于 2024-02-24 22:48
没用啊,能根据问题一继续修改吗?
抱歉没有为您解决问题。根据您的反馈,我注意到您的背景图像是`bg = pygame.image.load("waterfall.jpg")`,而在每一次循环中,您都使用`screen.blit(bg, bg_position)`将整个图像绘制到屏幕上。这可能导致闪烁问题,因为每次循环开始时,都会重新绘制整个图像。
为了解决这个问题,您可以尝试使用`pygame.Surface`对象作为画布,并在每次循环中只绘制变化的部分。代码如下:
import pygame
import sys
from pygame.locals import *
pygame.init()
size = width, height = 600, 400
bg_colour = (255, 255, 255)
fullscreen = False
modes = pygame.display.list_modes()
clock = pygame.time.Clock()
bg = pygame.image.load("waterfall.jpg")
bg_position = bg.get_rect()
canvas = pygame.Surface(size)# 创建画布
while True:
for event in pygame.event.get():
if event.type == QUIT:
sys.exit()
if event.type == KEYDOWN:
if event.key == K_F4:
fullscreen = not fullscreen
if fullscreen:
screen = pygame.display.set_mode(modes, FULLSCREEN | HWSURFACE)
else:
screen = pygame.display.set_mode(size)
canvas.fill(bg_colour)# 在画布上填充背景颜色
canvas.blit(bg, bg_position)# 绘制背景图像到画布上
screen.blit(canvas, (0, 0))# 将画布绘制到屏幕上
pygame.display.flip()
clock.tick(100)
通过这样的修改,您只需要在循环中更新画布上的变动部分,而不是每次都重新绘制整个图像。希望这次能解决您的闪烁问题!
以上回复来自 FishC AI 小助理,如未能正确解答您的问题,请继续追问。 FishC 发表于 2024-2-24 22:48
抱歉没有为您解决问题。根据您的反馈,我注意到您的背景图像是`bg = pygame.image.load("waterfall.jpg ...
还是不行啊 flyps 发表于 2024-02-24 22:52
还是不行啊
非常抱歉我的解决方案没有解决您的问题。闪烁问题可能是由于不同的原因引起的,这需要进一步的调试和排查。以下是几种可能的原因和解决方案:
1. 双缓冲技术:尝试使用双缓冲技术来减少闪烁。在你的代码中,创建一个额外的`pygame.Surface`对象,称为backbuffer。在每次循环中,首先绘制所有的图像到backbuffer上,然后将backbuffer一次性地绘制到屏幕上。这样可以避免在屏幕上的可见更新过程中出现闪烁。以下是修改的示例代码:
import pygame
import sys
from pygame.locals import *
pygame.init()
size = width, height = 600, 400
bg_colour = (255, 255, 255)
fullscreen = False
modes = pygame.display.list_modes()
clock = pygame.time.Clock()
bg = pygame.image.load("waterfall.jpg")
bg_position = bg.get_rect()
# 创建 backbuffer
backbuffer = pygame.Surface(size)
while True:
for event in pygame.event.get():
if event.type == QUIT:
sys.exit()
if event.type == KEYDOWN:
if event.key == K_F4:
fullscreen = not fullscreen
if fullscreen:
screen = pygame.display.set_mode(modes, FULLSCREEN | HWSURFACE)
else:
screen = pygame.display.set_mode(size)
backbuffer.fill(bg_colour)# 在 backbuffer 上填充背景颜色
backbuffer.blit(bg, bg_position)# 绘制背景图像到 backbuffer 上
screen.blit(backbuffer, (0, 0))# 将 backbuffer 绘制到屏幕上
pygame.display.flip()
2. 使用硬件加速:尝试使用硬件加速模式,以实现更平滑的绘制。在创建窗口时,将`screen`对象的标志位设置为`HWSURFACE`,这可以充分利用硬件来进行绘制:
screen = pygame.display.set_mode(size, HWSURFACE)
3. 降低帧率:减少程序的帧率可能会减少闪烁。可以尝试调整`clock.tick()`中的值,或者使用`pygame.time.delay()`在每一次循环中添加延迟。
如果以上解决方案仍然无法解决您的问题,我建议您检查您的硬件和驱动程序是否正常运行,并确保您的图像文件没有任何问题。另外,您还可以尝试在其他机器上运行您的代码,以查看是否存在特定于您当前计算机的问题。
以上回复来自 FishC AI 小助理,如未能正确解答您的问题,请继续追问。 你这看起来没问题啊{:10_277:}把waterfall.jpg发过来,我运行试试
页:
[1]