Why does this code work outside of the main loop in pygame

Viewed 129

I am new to using pygame and ive been following a tutorial on youtube. I ran into a problem with movement the guy in the tutorial was able to move by just holding down a button by i wasnt able. I had to continually tap the button i followed his code exactly.
I searched online and found that this code

(pygame.key.set_repeat(True)

could solve the problem but wasnt told where to put it so here is the code:

import pygame 
pygame.init()

win = pygame.display.set_mode((500,500))

pygame.display.set_caption("My First Pygame")

x = 50 
y = 425
width = 40
height = 60
vel = 5

isJump = True
jumpCount = 10 
pygame.key.set_repeat(True)
run = True
while run:
    pygame.time.delay(100)

    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            run = False

        keys = pygame.key.get_pressed()

        if keys[pygame.K_LEFT] and x > vel:
            x -= vel
        if keys[pygame.K_RIGHT]and x < 500 - width - vel:
            x += vel
        if not(isJump):    
            if keys[pygame.K_UP] and y > vel:
                y -=vel
            if keys[pygame.K_DOWN] and y < 500 -height - vel:
                y +=vel
            if keys[pygame.K_SPACE]:
                isJump = True
        else:
            if jumpCount >= -10:
                y -= (isJump ** 2) / 2
                jumpCount -= 1

            else:
                isJump = False
                jumpCount = 10


        win.fill((0,0,0))    
        pygame.draw.rect(win, (0,255,0), (x,y, width, height))
        pygame.display.update()


pygame.quit()

At first I had the code written under the line that says

keys = pygame.key.get_pressed() 

it didnt work but once i took it out of the main loop and put it before the while loop now it works. I can hold the key down and make my character move with out having to continually tap. My question is why does it work now.

1 Answers

It is a matter of Indentation. You have put the entire code in the event loop rather than in the application loop.
The event loop is executed once for each event. The application loop is executed once in each frame.
Each time when a button is pressed or released, then a button event is generated. The KEYDOWN and KEYUP event is returned by pygame.event.get() and the event loop is executed. For a continuous movement you have to get the current state of the keys in the application loop and to update the position of the object in every frame.

Move the code from the event loop to the application loop to solve the issue. e.g:

# application loop
run = True
while run:
    pygame.time.delay(100)

    # event loop
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            run = False

    #<--| INDENTATION!     
    keys = pygame.key.get_pressed()

    if keys[pygame.K_LEFT] and x > vel:
        x -= vel
    if keys[pygame.K_RIGHT]and x < 500 - width - vel:
        x += vel
    if not(isJump):    
        if keys[pygame.K_UP] and y > vel:
            y -=vel
        if keys[pygame.K_DOWN] and y < 500 -height - vel:
            y +=vel
        if keys[pygame.K_SPACE]:
            isJump = True
    else:
        if jumpCount >= -10:
            y -= (isJump ** 2) / 2
            jumpCount -= 1

        else:
            isJump = False
            jumpCount = 10

    win.fill((0,0,0))    
    pygame.draw.rect(win, (0,255,0), (x,y, width, height))
    pygame.display.update()

pygame.quit()
Related