I want to change the text in the controls screen based on the key which the user presses.
how do I convert pygame.event.get() into a string that shows which key has been pressed?
preferably without many if staments
for event in pygame.event.get():
if event.type == pygame.KEYDOWN:
slectedKey = # get key name as a string
print(slectedKey)
The code of the pressed can be get by the event.key attribute.
The unicode representation for the key can be get by the event.unicode attribute.
See pygame.event module.
A unser friendly name of a key can be get by pygame.key.name():
for event in pygame.event.get():
if event.type == pygame.KEYDOWN:
print(pygame.key.name(event.key))
Note, if you want to evaluate if a certain key is pressed, the compare event.key to the constants defined in the pygame.key module:
for event in pygame.event.get():
if event.type == pygame.KEYDOWN:
if event.key == pygame.K_LEFT:
# [...]
elif event.key == pygame.K_RIGHT:
# [...]
Or store the key in a variable and use it continuously in the application loop:
for event in pygame.event.get():
if event.type == pygame.KEYDOWN:
slectedKey = event.key
if slectedKey == pygame.K_UP:
# [...]
elif slectedKey == pygame.K_DOWN:
# [...]
If you want to evaluate if a key is is hold down, the use pygame.key.get_pressed():
for event in pygame.event.get():
if event.type == pygame.QUIT:
run = False
keys = pygame.key.get_pressed()
if keys[pygame.K_SPACE]:
# [...]
elif keys[pygame.K_a]:
# [...]
Related
I am trying to detect a single key press no matter how long the key is held down. Example, if the 'a' key is held down for 3 seconds, my current program would print this:
key pressed
'aaaaaaaaaaaaa'
key released
I am trying to get it to where it would only allow a single action per press/release cycle:
key pressed
'a'
key released
key pressed
'a'
key released
What am I doing wrong? Thank you
def update(self):
space_released = True
space_pressed = False
elif event.type == KEYUP:
if event.key == K_SPACE:
self.space_released = True
elif event.type == KEYDOWN:
if event.key == K_SPACE:
self.space_released = False
key = pygame.key.get_pressed()
while space_released == True:
# Print key pressed
return
space_released = False
Use pygame.key.set_repeat() to control how held keys are repeated:
When the keyboard repeat is enabled, keys that are held down will generate multiple pygame.KEYDOWN events. [...]
[...] To disable key repeat call this function with no arguments or with delay set to 0.
Just call pygame.key.set_repeat() to disable repeating keys:
pygame.key.set_repeat()
run = True
while run:
clock.tick(60)
space_released = False
space_pressed = False
for event in pygame.event.get():
if event.type == pygame.QUIT:
run = False
elif event.type == KEYUP:
if event.key == K_SPACE:
space_released = True
elif event.type == KEYDOWN:
if event.key == K_SPACE:
space_pressed = True
# [...]
If you want to do something similar with pygame.key.get_pressed (), you have to save the state of pygame.K_SPACE and compare the previous (space_was_pressed) state with the current state (space_is_pressed):
space_was_pressed = 0
run = True
while run:
clock.tick(60)
for event in pygame.event.get():
if event.type == pygame.QUIT:
run = False
key = pygame.key.get_pressed()
space_released = True
space_pressed = False
space_is_pressed = key[pygame.K_SPACE]
if space_was_pressed != space_is_pressed:
space_released = not space_is_pressed
space_pressed = space_is_pressed
space_was_pressed = space_is_pressed
for event in pygame.event.get():
if event.type == pygame.QUIT:
print('closing the window')
running = False
# key down for checking if a key is pressed.
if event.type == pygame.KEYDOWN:
print('some key is pressed')
if event.type == pygame.K_UP:
print("up key is pressed")
elif event.type == pygame.K_RIGHT:
print("Right key is pressed")
elif event.type == pygame.K_w:
print('w is pressed')
else:
print("does'nt recognize")
# key up for checking if a key is released.
if event.type == pygame.KEYUP:
print('some key is released')
if event.type == pygame.K_LEFT or event.type == pygame.K_RIGHT:
print('Keystroke is released')
I ran the code but this is the output:
some key is pressed
does'nt recognize
some key is released
some key is pressed
does'nt recognize
some key is released
closing the window
You are checking if event.type == pygame.K_RIGHT, however, you already know that event.type == pygame.KEYDOWN which is not equal to pygame.K_RIGHT. Instead, check event.key. This represents what key exactly is being pressed, while type just tells you that this is a keyboard event.
I know this question can be seen as a duplicate, but I spent some hours searching and figuring out what is wrong at my code.
My problem is that my object, called player, doesn't move constantly when left or right key is being held down:
for event in pygame.event.get():
if event.type == QUIT:
self.terminate()
if event.type == KEYDOWN:
if event.key == K_ESCAPE:
self.terminate()
if event.key == K_LEFT or event.key == K_a:
self.moveRight = False
self.moveLeft = True
if event.key == K_RIGHT or event.key == K_d:
self.moveLeft = False
self.moveRight = True
if event.type == KEYUP:
if event.key == K_LEFT or event.key == K_a:
self.moveLeft = False
if event.key == K_RIGHT or event.key == K_d:
self.moveRight = False
# Move the player around
if self.moveLeft :
# Moves the player object to left with self.PLAYERMOVERATE pixels.
self.player.setLeftRight(-1 * self.PLAYERMOVERATE)
if self.moveRight :
self.player.setLeftRight(self.PLAYERMOVERATE)
I also tried this alternative:
while True:
keys = pygame.key.get_pressed()
if keys[pygame.K_LEFT]:
self.player.setLeftRight(-1 * self.PLAYERMOVERATE)
if keys[pygame.K_RIGHT]:
self.player.setLeftRight(self.PLAYERMOVERATE)
I think that the problem is that you are not handling the input in the main game loop.
In your code you seem to be handling the input inside a method of the object Player. This is not how input should be handled. In your second code example there is a while True: loop which will mean the loop is never exited from and thus the method's execution is never finished. I suspect that there may be a similar issue in your first example.
Instead you should:
Create all objects and classes.
Write the main game loop.
The main game loop should handle input, then process the logic of the game and then render whatever should be rendered.
Here is a short code example.
while True:
for event in pygame.event.get():
if event.type == pygame.QUIT:
pygame.quit() # Exit from pygame window
quit() # End python thread
if event.type == KEYDOWN:
if event.key == K_LEFT or event.key == K_a:
player.moveRight = False
player.moveLeft = True
if event.key == K_RIGHT or event.key == K_d:
player.moveLeft = False
player.moveRight = True
if event.type == KEYUP:
if event.key == K_LEFT or event.key == K_a:
player.moveLeft = False
if event.key == K_RIGHT or event.key == K_d:
player.moveRight = False
# Move player using method
if player.moveLeft:
# Move player
# ...
# Render player
I hope that this helped you and if you have any further questions please feel free to post them in the comment section below!
I am trying to get user keyboard input using pygame. However, the problem is that after I run my code on IDLE, the keyboard input is never read by the program, and whatever I type is shown on the shell. Same issue if I run my code on PyCharm. Any idea? Below is my code:
pygame.init()
screen = pygame.display.set_mode((800, 600))
running = True
while running:
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
elif event.type == KEYDOWN and event.key == pygame.K_w:
print("Yup!")
pygame.display.flip()
I'm having the exact same issue, also on a Mac using Pycharm and python 3.6. I'm printing the events and only MouseMotion events are recorded, rather than KeyDown.
Edit: apparently it's a known issue: Window does not get focus on OS X with Python 3
This is my code, and it also should work:
while not crashed:
for event in pygame.event.get():
print(event)
if event.type == pygame.QUIT:
crashed = True
# get current list
pressed = pygame.key.get_pressed()
if pressed[pygame.K_UP]:
print("UP")
if event.type == pygame.KEYDOWN:
if event.key == pygame.K_1:
print('this DOES work! :)')
elif event.key == pygame.K_LEFT:
x_change = -5
elif event.key == pygame.K_RIGHT:
x_change = 5
elif pressed[pygame.K_UP]:
print("UP")
if event.type == pygame.KEYUP:
if event.key == pygame.K_LEFT or event.key == pygame.K_RIGHT:
x_change = 0
pygame.display.flip()
x += x_change
gameDisplay.fill(black)
ship(x, y)
pygame.display.update()
clock.tick(60)
This code works perfectly for me
import pygame
pygame.init()
windowSize = width,height = 800,600
screen = pygame.display.set_mode(windowSize)
running = True
while running:
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
quit()
elif event.type == pygame.KEYDOWN:
if event.key == pygame.K_w:
print("Yup!")
pygame.display.flip()
Here is some pygame code it works fine except to move the sprite i have to repeatedly tap the arrow keys, is there a way to make the sprite move by holding down the arrow keys? Below is my code:
while True: #main game loop
for event in pygame.event.get():
if event.type == QUIT:
pygame.quit()
sys.exit()
elif event.type == KEYUP:
if event.key == K_RIGHT:
LionCubX+= 10
elif event.key == K_LEFT:
LionCubX-= 10
elif event.key == K_UP:
LionCubY-= 10
elif event.key == K_DOWN:
LionCubY+= 10
DISPLAYSURF.fill(GREEN)
DISPLAYSURF.blit(LionCubImg,(LionCubX,LionCubY))
pygame.display.update()
The problem that I can see here is that you check for events of type KEYUP. This means that your Code only gets executed when you release the key. So change
elif event.type == KEYUP:
to
elif event.type == KEYDOWN:
Another possibility would be that you didn't set key repeat:
pygame.key.set_repeat(1, 30)
Put this before your main game loop to activate key repeat. Also see the docs.
The problem is you're moving your sprite only if a key has been depressed and released KEYUP. You need to move the sprite in the key state KEYDOWN.
Change this:
elif event.type == KEYUP:
To:
elif event.type == KEYDOWN: