Pygame屏幕在屏幕上移动线时撕裂

问题描述 投票:3回答:1

我想移动这个图像:

在我的PyGame屏幕上,从右到左,然后再返回,但是当图像移动时,每隔一秒左右,我有一个闪烁的屏幕撕裂,如图所示:

我使用的代码是一个类似于这样的循环:

screen.blit(img, (x,y))
pygame.update((x,y),(w,h))
pygame.draw.rect(screen,(0,0,0),((x,y),(w,h)))

到目前为止,我已尝试以下方法来解决此问题:

在创建屏幕时使用HWSURFACEFULLSCREENDOUBLEBUF标志,这没有效果,我还调整了我的.update(rect).flip()(因为这是建议使用DOUBLEBUF?)

拆分GPU和CPU之间的内存(我在覆盆子pi 2上运行)我试过给两个更多的内存,没有变化。

设置一个clock.tick来将更新速率限制在60 FPS(上下也是如此),这确实平滑了一些撕裂但不是全部

向左或向右调整每个增量的大小,使增量更小可以减少撕裂,但速度也会降低。 (不能让它变得太慢)

模仿新的黑色表面,而不是在前一个位置绘制黑色矩形(当移动图像以确保其后面没有任何痕迹时),因为我在某处读到blitHWSURFACE更好地支持而不是绘图,尽管我无法证实这一点? - 这没有效果

如果有人有任何其他可能改善情况的解决方案,我将不胜感激。

我宁愿不从PyGame改为其他任何东西(比如pyglet),因为到目前为止我已经使用PyGame完成了很多实现,但我愿意接受建议。

干杯

编辑

要求的相关代码:

if scanner == True:
    clocker.tick(clockspeed)
    if x < 11:
        slower = 3
        if firstTime == True:
            img.set_alpha(int(x * 25))
            newSurf.set_alpha(int(x * 25))
            screen.blit(newSurf,(xText,35))
            pygame.display.update((xText,35),((xText + newSurf.get_width()),(50 + newSurf.get_height())))
            img.set_alpha(255)

    elif x > (divider - 15):
        slower = 3
    else:
        slower = 0
        firstTime = False

    screen.blit(img, ((xStart - (x * increment) + slower),100))
    pygame.display.update(((xStart - (x * increment) + slower),100),(95,450))
    pygame.draw.rect(screen, (0,0,0), (((xStart - (x * increment) + slower),100),(95,450)))

slower变量是为了给出一种惯性的感觉,当杆到达其扫过的最左侧和右侧时,速度会慢一点。

firstTime变量用于首次出现时在条形图中淡入淡出。

在此下面还有另一个非常相似的循环,但是以另一种方式扫描图像。

python pygame raspberry-pi vsync
1个回答
0
投票

这种撕裂只是屏幕渲染方式的产物。该线的下一个位置是在绘制前一个位置时进行渲染。如果屏幕的刷新率和更新率是同步的,则此问题将消失。但由于几乎不可能准确地做到这一点,我建议让你的程序采用PICO-8管理它的路线,等待屏幕刷新完成后再更改屏幕缓冲区以防止撕裂。我不确定是否有等待屏幕刷新完成的方法,但是如果有,那么序列应该是:update back buffer -> wait for screen to stop being drawn -> flip buffers -> screen is drawn again

刷新是从左到右,从上到下,逐个像素地绘制屏幕的地方。这是因为到屏幕的三重BUS连接只允许一次一个像素的亮度来自屏幕存储器,因此每个像素都按顺序绘制。撕裂来自于在刷新过程中途的记忆变化,因此线条在屏幕中间移动位置。

© www.soinside.com 2019 - 2024. All rights reserved.