Pause system in pygame [duplicate] - python

This question already has answers here:
Why is my pause system not working in Pygame?
(2 answers)
Closed 8 years ago.
hi there i've spent hours trying to make a toggle pause in pygame that you press space and it pauses then you press space again to un-pause and i'm having no luck would any one be able to help me please?
############### 2nd attempt #############
global timedelay
timedelay = pygame.time.wait (0)
pause = 0
if event.type == KEYUP:
if event.key == K_p and pause == 0:
timedelay = pygame.time.wait (9999)
pause = 1
if event.key == K_p and pause == 0:
timedelay = pygame.time.wait (0)
pause = 0
timedelay
############### 1st attempt #############
if event.type == KEYDOWN:
pause = 0
if event.key == K_p and pause == 0:
while 1:
pause = 0
event = pygame.event.wait()
pause = 1
if event.type == KEYDOWN:
if event.key == K_p and pause == 0:
print "woo!"
pause = 0
break

Don't block your whole main loop from running, just skip the state change part of the loop. You still need to be able to respond to events or your app is "unresponsive". You also want to keep drawing as windows can be moved around and cover your game and the screen still needs to refresh. So:
game_over = False
paused = False
while not game_over:
# handle events
for event in pygame.event.get():
if event.type == KEYDOWN:
paused = False
if event.key == K_p:
paused = True
...
if not paused:
# handle game state change
# handle screen drawing
pygame.display.flip()

Related

My pause statement is not working for pygame loop

My collide_rect function is not working as I expect to be. The problem is when press the key 'r', it should be able to reset everything and continue the game. But when I actually press the key 'r', it does not change anything when I add in the pause statement. I want to have the game pause when two of the sprites I have(ball, obstacle) collide. After the user inputs the letter 'r', it should go back to running and reset position for both sprites. The error I am getting is when I press the key 'r', it does not change anything on the surface.
This is my while loop:
paused = False
def display_text(text):
font = pygame.freetype.Font('helvetica.ttc', 32)
text_attributed = font.render_to(gameDisplay, (300,300), text, black)
while not crashed:
time = pygame.time.get_ticks()
obstacle.change_x()
for event in pygame.event.get():
if event.type == pygame.QUIT:
crashed = True
if event.type == pygame.KEYDOWN:
if event.key == pygame.K_UP:
ball.jump_true()
if event.key == pygame.K_SPACE:
ball.jump_true()
if event.key == pygame.K_r:
paused = not paused
if ball.collide == True:
gameDisplay.fill(white)
display_text('You Lost! type "R" to restart')
paused = True
if paused == True:
ball.reset_position()
obstacle.reset_position()
pygame.display.flip()
clock.tick(20)
else:
ball.jump()
ball.test_collision(obstacle)
gameDisplay.fill(white)
ball.update()
obstacle.update()
pygame.display.flip()
clock.tick(60)
pygame.quit()
sys.exit()
Don't overcomplicate things. You don't need multiple event loops. Use 1 main loop, 1 event loop and a state which indicates if the game is paused. e.g.:
paused = False
run = True
while run:
for event in pygame.event.get():
if event.type == pygame.QUIT:
run = False
if event.type == pygame.KEYDOWN:
if event.key == pygame.K_r
# Toggle pause
paused = not paused
if paused:
# "pause" mode
# [...]
else
# "run" mode
# [...]
# update display etc.
# [...]

Call function by button click in Pygame

I got a screen with buttons in Pygame here in the code below. Now I want to click the button, then a random() function starts and after 5 seconds it returns to the screen from the beginning with the buttons and let me the option to click again and call a random function again.
def loop():
clock = pygame.time.Clock()
number = 0
# The button is just a rect.
button = pygame.Rect(300,300,205,80)
done = False
while not done:
for event in pygame.event.get():
if event.type == pygame.QUIT:
done = True
# This block is executed once for each MOUSEBUTTONDOWN event.
elif event.type == pygame.MOUSEBUTTONDOWN:
# 1 is the left mouse button, 2 is middle, 3 is right.
if event.button == 1:
# `event.pos` is the mouse position.
if button.collidepoint(event.pos):
# Incremt the number.
number += 1
random()
loop()
pygame.quit()
Add a state variable (runRandom), which indicates if the the function random has to be run:
runRandom = False
while not done:
# [...]
if runRandom:
random()
Add user defined pygame.event, which can be used for a timer:
runRandomEvent = pygame.USEREVENT + 1
for event in pygame.event.get():
# [...]
elif event.type == runRandomEvent:
# [...]
Allow the button to be pressed if random ins not running. If the button is pressed then state runRandom and start the timer (pygame.time.set_timer()) with the decided period of time (e.g. 5000 milliseconds = 5 seconds):
# [...]
elif event.type == pygame.MOUSEBUTTONDOWN:
if event.button == 1:
if button.collidepoint(event.pos) and not runRandom:
# [...]
runRandom = True
pygame.time.set_timer(runRandomEvent, 5000)
When the time has elapse, the stop running random by runRandom = False and stop the timer:
# [...]
elif event.type == runRandomEvent:
runRandom = False
pygame.time.set_timer(runRandomEvent, 0)
Apply the suggestion to your code somehow like this:
# define user event for the timer
runRandomEvent = pygame.USEREVENT + 1
def loop():
clock = pygame.time.Clock()
number = 0
# The button is just a rect.
button = pygame.Rect(300,300,205,80)
done = False
runRandom = False
while not done:
for event in pygame.event.get():
if event.type == pygame.QUIT:
done = True
# This block is executed once for each MOUSEBUTTONDOWN event.
elif event.type == pygame.MOUSEBUTTONDOWN:
# 1 is the left mouse button, 2 is middle, 3 is right.
if event.button == 1:
# `event.pos` is the mouse position and "random" is not running
if button.collidepoint(event.pos) and not runRandom:
# Incremt the number.
number += 1
# Start timer and enable running "random"
runRandom = True
pygame.time.set_timer(runRandomEvent, 5000) # 5000 milliseconds
elif event.type == runRandomEvent:
runRandom = False
pygame.time.set_timer(runRandomEvent, 0)
# [...]
# run "random"
if runRandom:
random()
# [...]

Continuous object creation in pygame?

Okay, so I've researched this topic a bit. I'm creating a game in Python's Pygame, a replica of the famous "Raiden 2". My game loop is fairly similar to those I've seen around. What I'm trying to do is have the constructor create a bullet object (with my Bullet class) while the space bar is being held. However, the following code only creates a single bullet per keypress. Holding the button does nothing, just creates a single bullet.
while game.play is True:
for event in pygame.event.get():
if event.type == pygame.KEYDOWN:
if event.key == pygame.K_SPACE:
b = Bullet(x, y)
bullet_group.add(b)
bullet_group.draw(screen)
Not sure where to go from here. Any help is welcome and appreciated.
This should work as you expect it:
addBullets = False
while game.play is True:
for event in pygame.event.get():
if event.type == pygame.KEYDOWN:
if event.key == pygame.K_SPACE:
addBullets = True
if event.type == pygame.KEYUP:
if event.key == pygame.K_SPACE:
addBullets = False
if addBullets:
b = Bullet(x, y)
bullet_group.add(b)
bullet_group.draw(screen)
You move the creation of bullets out of the handling of events and set there only a "flag" which is taken back if the key is released stopping creation of bullets.
And ... as mentioned in the comment by jsbueno this will work too:
while game.play is True:
for event in pygame.event.get():
pass # do something with events
if pygame.key.get_pressed()[pygame.K_SPACE]:
b = Bullet(x, y)
bullet_group.add(b)
I think the other answer is lacking an important detail. You most likely don't want to fire a bullet every frame, so you need to have some kind of timer. The simplest way is to count the frames, but then the game would be frame rate bound (better don't do it in this way).
firing = False
bullet_timer = 0
while game.play:
for event in pygame.event.get():
if event.type == pygame.QUIT:
game.play = False
if event.type == pygame.KEYDOWN:
if event.key == pygame.K_SPACE:
firing = True
elif event.type == pygame.KEYUP:
if event.key == pygame.K_SPACE:
firing = False
if bullet_timer > 0:
bullet_timer -= 1
elif firing: # Timer is less than 0 and we're firing.
bullet = Bullet()
bullet_group.add(bullet)
bullet_timer = 10 # Reset timer to 10 frames.
The frame rate independent variant is to use the time that pygame.Clock.tick returns (the time that has passed since it was called the last time) and subtract it from the timer variable. If the timer is <= 0 we're ready to fire.
clock = pygame.time.Clock()
firing = False
bullet_timer = 0
while game.play:
# `dt` is the passed time since the last tick in seconds.
dt = clock.tick(30) / 1000
for event in pygame.event.get():
if event.type == pygame.KEYDOWN:
if event.key == pygame.K_SPACE:
firing = True
elif event.type == pygame.KEYUP:
if event.key == pygame.K_SPACE:
firing = False
if bullet_timer > 0:
bullet_timer -= dt
elif firing: # Timer is below 0 and we're firing.
bullet = Bullet()
bullet_group.add(bullet)
bullet_timer = .5 # Reset timer to a half second.

pygame mouse button down not working

I am making this multiple choice program, but I need the mouse event to only work after enter is pressed.
Here is my code:
for event in pygame.event.get(): # If user did something
if event.type == pygame.QUIT: # If user clicked close
done = True
elif event.type == pygame.KEYDOWN: # If user pressed a key
if event.key == pygame.K_RETURN: # If user pressed enter
# Makes the start screen go away
enter_pressed = True
# Increments question_number
question_number += 1
# Where I Draw the question screen
Then down below I have this:
for event in pygame.event.get(): # If user did something
if event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:
print("Derp")
Derp won't print when I press left mouse button.
However, when I have it indented like this:
for event in pygame.event.get(): # If user did something
if event.type == pygame.QUIT: # If user clicked close
done = True
elif event.type == pygame.KEYDOWN: # If user pressed a key
if event.key == pygame.K_RETURN: # If user pressed enter
# Makes the start screen go away
enter_pressed = True
# Increments question_number
question_number += 1
# Where I Draw the question screen
elif event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:
print("Derp")
Derp does print when I press left mouse button
You could use a boolean indicating wheter or not enter was pressed.
for event in pygame.event.get(): # If user did something
enter_pressed = False
if event.type == pygame.QUIT: # If user clicked close
done = True
elif event.type == pygame.KEYDOWN: # If user pressed a key
if event.key == pygame.K_RETURN: # If user pressed enter
# Makes the start screen go away
enter_pressed = True
# Increments question_number
question_number += 1
# Where I Draw the question screen
elif event.type == pygame.MOUSEBUTTONDOWN and event.button == 1 and enter_pressed:
print("Derp")
I think that the problem is that you are iterating over all events, and inside that loop you are iterating over all events (again), and that causes some problems
It is hard to tell from what you said, but I have a couple of recommendations for you. First, make sure that the for loop with derp isn't in any if statements you don't want it to be in. Second, make sure you call pygame.event.get() once per game loop or the code will only give you events that happened between the two calls, which will not be all of them. If neither of these things work, try posting the whole code.

Python - Pygame - Learning get_pressed

I am learning python as well as pygame. I am struggling a bit with finding the issue in my code. When I hold down a key and press another key at the same time, and then let go of them in the same order I press them, it sometimes makes my little character move backwards in the opposite direction.
Here is my code that I am struggling with:
while running:
for event in pygame.event.get():
if event.type == KEYDOWN:
keystate = pygame.key.get_pressed()
if event.type == pygame.QUIT: # if user clicked close
running = False # flag done to exit this loop
# all game logic / controls should go below this comment
elif event.type == KEYDOWN:
if keystate[K_SPACE]:
print ('pressed space')
player.move_up = True
elif keystate[K_RIGHT]:
print ('pressed right')
player.move_right = True
elif keystate[K_LEFT]:
print ('pressed left')
player.move_left = True
elif event.type == KEYUP:
if keystate[K_SPACE]:
print ('released space')
player.move_up = False
elif keystate[K_RIGHT]:
print ('released right')
player.move_right = False
elif keystate[K_LEFT]:
print ('released left')
player.move_left = False
if player.move_up:
player.pos[1] -= 3
if player.move_up == False:
if player.pos[1] < ground_level:
player.pos[1] +=3
if player.move_right:
player.pos[0] += 5
if player.move_left:
player.pos[0] -= 5`
So far I don't have any actual physics, and he just flies around. But that's okay, I just want to iron out the issues that I am already having.
You never update keystate's value on a KEYUP event. Thus, it still has whatever values it had whenever the last KEYDOWN event fired.
To fix this, change this...
if event.type == KEYDOWN:
keystate = pygame.key.get_pressed()
to this:
if event.type in (KEYDOWN, KEYUP):
keystate = pygame.key.get_pressed()

Categories