3

Can someone please help me debug my code because I don't get why I cannot make my character do a double jump with multiple spacebars. When I ran the script, I could move up,down,left,right but once I press spacebar one time, the object flies out of the window.

The problem comes with this if statement so I'm guessing that this if statement keeps running and incrementing my jumpCount, which I can't comprehend because after pressing space one time shouldn't the keys[pygame.K_SPACE] evaluate to true and then back to false again so this if statement shouldn't run unless I press another spacebar?

else:
    if keys[pygame.K_SPACE]:
        jumpCount += 5
        number_to_compensate += 1

Here is my script:

import pygame

pygame.init()

win = pygame.display.set_mode((500, 500))
pygame.display.set_caption("First Game")

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

isJump = False

jumpCount = 5 #To calculate the height I have to rise by
number_to_compensate = 0 #So the more times I press space(higher I jump) the more I have to fall by

run = True

while run:
    pygame.time.delay(20)

    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 - vel - width:
        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
            number_to_compensate += 1
    else:
        if keys[pygame.K_SPACE]:
            jumpCount += 5
            number_to_compensate += 1
        if jumpCount >= -5 *number_to_compensate:
            y -= (jumpCount * abs(jumpCount)) * 0.5
            jumpCount -= 1
        else:
            jumpCount = 5
            isJump = False
            number_to_compensate = 0



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

pygame.quit()
Rabbid76
  • 202,892
  • 27
  • 131
  • 174
  • Please provide the expected see [MRE - Minimal, Reproducible Example](https://stackoverflow.com/help/minimal-reproducible-example). Show where the intermediate results deviate from the ones you expect. We should be able to paste a single block of your code into file, run it, and reproduce your problem. This also lets us test any suggestions in your context. We also expect that you will trace the suspect values just before the point of error. Where are you confused about how they got to those values? So far, you haven't traced *anything*. – Prune May 24 '21 at 05:59
  • Yes, I understand the effect. Please read my suggestions again, as well as the MRE standards. OP is responsible to make a reasonable attempt at debugging the code, but has not shown any evidence to that end. – Prune May 24 '21 at 06:15
  • Is the issue solved? – Rabbid76 May 28 '21 at 19:13

1 Answers1

5

To what you want you need to change some the jump algorithm. Calculate the jump based on an acceleration and a velocity.

Define constants for the gravity and jump acceleration:

PLAYER_ACC = 15
PLAYER_GRAV = 1

Use the keyboard events for the jump, instead of pygame.key.get_pressed(). The keyboard events (see pygame.event module) occur only once when the state of a key changes. The KEYDOWN event occurs once every time a key is pressed. KEYUP occurs once every time a key is released. Use the keyboard events for a single action.
Set the jump acceleration when the space is pressed:

acc_y = PLAYER_GRAV
for event in pygame.event.get():
    if event.type == pygame.QUIT:
        run = False
    if event.type == pygame.KEYDOWN:
        if event.key == pygame.K_SPACE:
            acc_y = -PLAYER_ACC
            vel_y = 0

Change the velocity depending on the acceleration and the y coordinate depending on the velocity in every frame:

vel_y += acc_y
y += vel_y

Limit the y-coordinate by the ground:

if y + height > ground_y:
    y = ground_y - height
    vel_y = 0
    acc_y = 0

Minimal example:

import pygame

pygame.init()
win = pygame.display.set_mode((500, 500))
pygame.display.set_caption("First Game")
clock = pygame.time.Clock()

ground_y = 400
x, y = 200, ground_y
width, height = 40, 60
vel_x, vel_y = 5, 0
acc_y = 0

PLAYER_ACC = 15
PLAYER_GRAV = 1

run = True
while run:
    acc_y = PLAYER_GRAV
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            run = False
        if event.type == pygame.KEYDOWN:
            if event.key == pygame.K_SPACE:
                acc_y = -PLAYER_ACC
                vel_y = 0

    keys = pygame.key.get_pressed()
    x += (keys[pygame.K_RIGHT] - keys[pygame.K_LEFT]) * vel_x
    x = max(0, min(500 - width, x))

    vel_y += acc_y
    y += vel_y

    if y + height > ground_y:
        y = ground_y - height
        vel_y = 0
        acc_y = 0

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

pygame.quit()
Rabbid76
  • 202,892
  • 27
  • 131
  • 174