Pygame: Display not updating until after delay - python

I have a bug in the program I am writing where I first call:
pygame.display.update()
Then I call:
pygame.time.wait(5000)
I want the program to update the display and then wait for a set period of time before continuing. However for some reason the display only updates after the waiting time, not before.
I have attached some example code to demonstrate what is happening:
import pygame
pygame.init()
white = (255,255,255)
black = (0,0,0)
green = (0,255,0)
screenSize = screenWidth, screenHeight = 200, 200
screen = pygame.display.set_mode(screenSize)
screen.fill(white)
pygame.draw.rect(screen, black,((50,50),(50,50)))
pygame.display.update()
pygame.time.wait(5000)
pygame.quit()
raise SystemExit
This should create a white window with black box, then wait 5 seconds and then quit.
However what it actually does is make a window, wait 5 seconds, then for a split second the box will appear, then it immediately quits.
Does anyone know how to fix this problem?

Your window's content will only be drawn if your window manager tells your window to actually paint something. So if your code works depends on your window manager.
What you should do to make it work is to let pygame process all events, and you do it usually by calling pygame.event.get().
Also, you should avoid calling blocking functions like pygame.time.wait(), since while they block, you can't handle events or let pygame process system events. That means pygame won't repaint the window, and you can't close the window.
Consider changing your code to this:
import pygame
pygame.init()
white = (255,255,255)
black = (0,0,0)
green = (0,255,0)
screenSize = screenWidth, screenHeight = 200, 200
screen = pygame.display.set_mode(screenSize)
screen.fill(white)
pygame.draw.rect(screen, black,((50,50),(50,50)))
run = True
clock = pygame.time.Clock()
dt = 0
while run:
dt += clock.tick()
for e in pygame.event.get():
if e.type == pygame.QUIT:
run = False
if dt >= 5000:
run = False
pygame.display.update()

Related

Python Not Responding when I Run it

Python doesn't respond when I play it. No syntax error appears either. Not sure what is wrong. I tried running another game I made which worked fine so I don't think it's my computer.
error message
This is my code:
import pygame
pygame.init()
screen = pygame.display.set_mode((800,600))
pygame.display.set_caption("Draft")
icon = pygame.image.load("doctor.png")
pygame.display.set_icon(icon)
white = (255,255,255)
black = (0,0,0) red = (255,0,0)
green = (0,255,0)
blue = (0,0,255)
def draw_ground():
groundx = 20
groundy = 30
Ground = pygame.Rect(groundx,groundy,width = 800,height = 20)
pygame.draw.rect(screen,green,Ground)
running = True
while running:
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
draw_ground()
It isn't complete yet, I'm trying to test it first before moving ahead.
There is a typo in your code:
black = (0,0,0) red = (255,0,0)
It has to be
black = (0,0,0)
red = (255,0,0)
However, there is more.
pygame.Rect does not accept keyword arguments:
Ground = pygame.Rect(groundx,groundy,width = 800,height = 20)
Ground = pygame.Rect(groundx,groundy,800,20)
You have to update the display by calling either pygame.display.update() or pygame.display.flip():
clock = pygame.time.Clock()
running = True
while running:
clock.tick(60)
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
# clear dispaly
screen.fill(0)
# draw objects
draw_ground()
# update dispaly
pygame.display.flip()
The typical PyGame application loop has to:
limit the frames per second to limit CPU usage with pygame.time.Clock.tick
handle the events by calling either pygame.event.pump() or pygame.event.get().
update the game states and positions of objects dependent on the input events and time (respectively frames)
clear the entire display or draw the background
draw the entire scene (blit all the objects)
update the display by calling either pygame.display.update() or pygame.display.flip()

pygame screen only works when i move the window off the screen

import pygame, sys
from pygame.locals import *
pygame.init()
sizex = 400
sizey = 300
tilesize = 25
tile = pygame.image.load('images/tile.png')
tile = pygame.transform.scale(tile, (tilesize, tilesize))
screen = pygame.display.set_mode((sizex,sizey))
while True:
for event in pygame.event.get():
if event.type == QUIT:
pygame.quit()
sys.exit()
for row in range(sizex):
for column in range(sizey):
screen.blit(tile,(column*tilesize, row*tilesize,tilesize,tilesize))
I am using this code to output:
however, when I run it the screen is black,
if i move half of the window off of the computer screen:
and move it back:
that happens.
Can someone pls explain why this happens and how to fix it.
The reason for this is most likely that nothing triggers a re-draw event. Meaning the buffer never updates. Except when the window is moved outside of the screen, that portion will trigger a re-draw event for that area.
Manually adding a update or flip at the end of your while, should force a update of the scene, making things look nice again:
import pygame, sys
from pygame.locals import *
pygame.init()
sizex = 400
sizey = 300
tilesize = 25
tile = pygame.image.load('images/tile.png')
tile = pygame.transform.scale(tile, (tilesize, tilesize))
screen = pygame.display.set_mode((sizex,sizey))
while True:
for event in pygame.event.get():
if event.type == QUIT:
pygame.quit()
sys.exit()
for row in range(sizex):
for column in range(sizey):
screen.blit(tile,(column*tilesize, row*tilesize,tilesize,tilesize))
pygame.display.flip() # or pygame.display.update()
For anyone familiar with pygame/gl and screen updates, this will be some what taxing. In ideal cases, you would only update areas that are in need of updates.
For instance, keeping track of which portions of the screen you've moved a character, or which mouse events have triggered certain elements on the screen. And then only do pygame.display.update(rectangle_list) with a area to update.
Here's a good description of what the two does and why using update() might be a good idea: Difference between pygame.display.update and pygame.display.flip

Pygame program failing to draw as expected

I am new to pygame, and I was expecting the display be cyan and the rectangle to be drawn. The window appears but not in cyan and without the rectangle?
I believe it has something to do with the order or spacing.
Everything was working before I added the rect.
import pygame
import sys
from pygame.locals import *
pygame.init()
cyan = (0,255,255)
soft_pink = (255,192,203)
screen_width = 800
screen_height = 600
gameDisplay = pygame.display.set_mode((screen_width, screen_height))
pygame.display.set_caption('''example''')
pygame.draw.rect(gameDisplay,soft_pink,(389,200),(300,70),4)
gameDisplay.fill(cyan)
gameExit = True
while True:
for event in pygame.event.get():
if event.type == QUIT:
pygame.quit()
sys.exit()
pygame.display.update()
You should be very careful with your formatting for Python code. Testing your code and fixing up the formatting for the while loop reveals the problem:
C:\src\python\pygame1>python buggy.py
Traceback (most recent call last):
File "buggy.py", line 16, in <module>
pygame.draw.rect(gameDisplay,soft_pink,(389,200),(300,70),4)
TypeError: function takes at most 4 arguments (5 given)
If you just replace the pygame.draw.rect call with the correct number of parameters it shows a cyan window. I tested the following replacement line:
pygame.draw.rect(gameDisplay,soft_pink,(389,200,300,70))
When initializing a pygame screen, a surface is returned which you can fill and should fill continuously in your while loop. I suggest you use a surface object for the rectangle as well. Just change your code like so:
import pygame
import sys
from pygame.locals import *
pygame.init()
cyan = (0,255,255)
soft_pink = (255,192,203)
screen_width = 800
screen_height = 600
gameDisplay = pygame.display.set_mode((screen_width, screen_height))
pygame.display.set_caption('Example') # shouldn't use triple quotes
gameExit = True
surf = pygame.Surface((200, 75)) # takes tuple of width and height
rect = surf.get_rect()
rect.center = (400, 300)
while True:
for event in pygame.event.get():
if event.type == QUIT:
pygame.quit()
sys.exit()
pygame.display.update()
gameDisplay.fill(cyan) # continuously paint screen cyan
surf.fill(soft_pink) # continuously paint rectangle
gameDisplay.blit(surf, rect) # position rectangle at position
Remember continuous rendering is the underlying secret to game development, and objects are painted in the order you specify. So in this case you'd actually see the rectangle because it's painted after the screen is.

When i make a pygame game and hover over it, the cursor turns into the loading thing

When i make a pygame game and hover over it, the cursor turns into the loading thing, that means I can't resize the window, or if i were to make buttons i wouldn't be able to use them... Help? Here's my code.
import pygame
import random
import time
import os
from pygame.locals import *
red = (255,0,0)
white = (255,255,255)
black = (0,0,0)
green = (0,255,0)
blue = (0,0,255)
pygame.init()
background_colour = (white)
(width, height) = (800, 600)
screen = pygame.display.set_mode((width, height), pygame.RESIZABLE)
screen.fill(background_colour)
while True:
pygame.draw.circle(screen,
(random.randint(0,255),
random.randint(0,255),random.randint(0,255)),
(random.randint(0,800),random.randint(0,600)), 20)
pygame.display.flip()
So yeah, it always happens with pygame.
Add this in top of your while.
This for runs throught events and if
event.type == pygame.QUIT
This means that you presed cross for closing the window and window will be closed. You can catch all pygame events like this.
while True: #your wile
for event in pygame.event.get():
if event.type == pygame.QUIT:
sys.exit()
#your code

Pygame script freezing on windows (Program not responding)

I am new to stackoverflow, I decided to join because I sometimes have problems with programming. This one is really annoying, I cant figure out why it doesn't work. Any help would be appreciated!
I get the windows "Program not responding" error message
A simple display:
import pygame
pygame.init()
BLUE = pygame.Color(0, 0, 255)
size = [1280, 720]
screen = pygame.display.set_mode(size)
pygame.display.set_caption("Hangman")
done = False
clock = pygame.time.Clock()
while not done:
# Leaves the fps at 30
clock.tick(30)
screen.fill(BLUE)
pygame.display.flip()
The expected result is a blue screen, instead I get a blue screen that crashes
In your game loop handling events will prevent freezing.
import pygame
pygame.init()
BLUE = pygame.Color(0, 0, 255)
size = [1280, 720]
screen = pygame.display.set_mode(size)
pygame.display.set_caption("Hangman")
done = False
clock = pygame.time.Clock()
while not done:
for event in pygame.event.get():
if event.type == pygame.QUIT:
sys.exit(0)
else:
print event
# Leaves the fps at 30
clock.tick(30)
screen.fill(BLUE)
pygame.display.flip()

Categories

Resources