Как я могу постоянно цикл KEYDOWN в Pygame? - PullRequest
0 голосов
/ 31 августа 2018

Я новичок в python / pygame и не могу понять это. Всякий раз, когда я нажимаю и удерживаю клавишу, она не зациклит KEYDOWN. Кроме того, если я удерживаю клавишу на клавиатуре и одновременно перемещаю мышь, кажется, что она движется непрерывно.

Может кто-нибудь сказать мне, что я делаю не так?

import pygame
import random
pygame.init()

#Colors
white = 255, 255, 255
black = 0, 0, 0
back_color = 48, 255, 124
light_color = 34, 155, 78

#Display W/H
display_width = 800
display_height = 600

#X/Y
x_axis = 400
y_axis = 580

Block_size = 20
x_int = 0
y_int = 0

ON = True



Window = pygame.display.set_mode((display_width, display_height))
pygame.display.set_caption('Game')



#On Loop
while ON == True:
    #Screen Event
    for Screen in pygame.event.get():
        #Quit Screen
        if Screen.type == pygame.QUIT:
            pygame.quit()
            exit()
        #Quit Full Screen
        if Screen.type == pygame.KEYDOWN:
            if Screen.key == pygame.K_q:
                pygame.quit()
                exit()

        #Full Screen !!!!!!!! EDIT THIS !!!!!!!!
        if Screen.type == pygame.KEYDOWN:
            if Screen.key == pygame.K_1:
                pygame.display.set_mode((display_width, display_height),pygame.FULLSCREEN)
            if Screen.key == pygame.K_2:
                pygame.display.set_mode((display_width, display_height))

        #Player Movement K DOWN
        if Screen.type == pygame.KEYDOWN:
            if Screen.key == pygame.K_d:
                x_int = 20
            if Screen.key == pygame.K_a:
                x_int = -20
       #Player Movement K UP
        if Screen.type == pygame.KEYUP:
            if Screen.key == pygame.K_d or Screen.key == pygame.K_a:
                x_int = 0

        x_axis += x_int



        Window.fill((back_color))
        Player = pygame.draw.rect(Window, light_color, [x_axis, y_axis, Block_size, Block_size])



        pygame.display.update()
quit()

Ответы [ 2 ]

0 голосов
/ 31 августа 2018

Я улучшил ваш код. Вы поместили часть обновления экрана (рисование экрана) в цикл событий, тогда как она должна быть в цикле while. Код, который у меня есть, немного сложен, но работает, как и ожидалось. Почему это сложно? Когда клавиша удерживается нажатой, список событий пуст (вы можете распечатать события). Я также сделал блок, чтобы не выходить за пределы экрана. Скорость блока была высокой, поэтому я уменьшил ее до 10.

import pygame
import random
pygame.init()

#Colors
white = 255, 255, 255
black = 0, 0, 0
back_color = 48, 255, 124
light_color = 34, 155, 78

#Display W/H
display_width = 800
display_height = 600

#X/Y
x_axis = 400
y_axis = 580
global x_int
Block_size = 20
x_int = 0
y_int = 0

ON = True



Window = pygame.display.set_mode((display_width, display_height))
pygame.display.set_caption('Game')

global topass_a,topass_d
x_int,topass_a,topass_d = 0,0,0
#On Loop
while ON:
    #Screen Event
    events = pygame.event.get()
    def on_a_press():
        global topass_a,x_int
        x_int = -10
        topass_a = 1
    def on_d_press():
        global topass_d,x_int
        x_int = 10
        topass_d = 1
    if len(events) == 0:
         if topass_a == 1:on_a_press()
         if topass_d == 1:on_d_press()
    for Screen in events:
        if Screen.type == pygame.QUIT:
            pygame.quit()
            exit()
        if Screen.type == pygame.KEYDOWN:
            if Screen.key == pygame.K_q:
                pygame.quit()
                exit()
            if Screen.key == pygame.K_1:
                    pygame.display.set_mode((display_width, display_height),pygame.FULLSCREEN)
            if Screen.key == pygame.K_2:
                    pygame.display.set_mode((display_width, display_height))
            if Screen.key == pygame.K_d or topass_d == 1:
                on_d_press()
            if Screen.key == pygame.K_a or topass_a == 1:
                on_a_press()
        if Screen.type == pygame.KEYUP:
            if Screen.key == pygame.K_d or Screen.key == pygame.K_a:
                x_int = 0
                topass_a = 0
                topass_d = 0

    x_axis += x_int
    x_int = 0
    if x_axis < 0:x_axis=0
    elif x_axis >= display_width-Block_size:x_axis = display_width-Block_size
    Window.fill((back_color))
    Player = pygame.draw.rect(Window, light_color, [x_axis, y_axis, Block_size, Block_size])
    pygame.display.update()

Вы можете улучшать код по мере необходимости.

Edit:

Почему сложный? Легкие вещи на первом месте. Я понял, что нет необходимости отслеживать ключи. pygame.key.get_pressed() возвращает нажатую клавишу. Вот меньший, лучший и улучшенный код. Я также реализовал клавиши w и s (y_axis).

import pygame
import random
pygame.init()

#Colors
white = 255, 255, 255
black = 0, 0, 0
back_color = 48, 255, 124
light_color = 34, 155, 78

#Display W/H
display_width = 800
display_height = 600

#X/Y
x_axis = 400
y_axis = 580
Block_size = 20
x_int = 0
y_int = 0

ON = True



Window = pygame.display.set_mode((display_width, display_height))
pygame.display.set_caption('Game')
while ON:
    events = pygame.event.get()
    for Screen in events:
        if Screen.type == pygame.QUIT:
            pygame.quit()
            exit()
        if Screen.type == pygame.KEYDOWN:
            if Screen.key == pygame.K_q:
                pygame.quit()
                exit()
            if Screen.key == pygame.K_1:
                    pygame.display.set_mode((display_width, display_height),pygame.FULLSCREEN)
            if Screen.key == pygame.K_2:
                    pygame.display.set_mode((display_width, display_height))

    keys = pygame.key.get_pressed()
    if keys[pygame.K_a]:
        x_int = -10
    if keys[pygame.K_d]:
        x_int = 10
    # keys controlling y axis, you can remove these lines
    if keys[pygame.K_w]:
        y_int = -10
    if keys[pygame.K_s]:
        y_int = 10
    #x_axis......
    x_axis += x_int
    x_int = 0
    if x_axis < 0:x_axis=0
    elif x_axis >= display_width-Block_size:x_axis = display_width-Block_size
    #y axis
    y_axis += y_int
    y_int = 0
    if y_axis < 0:y_axis=0
    elif y_axis >= display_height-Block_size:y_axis = display_height-Block_size
    #updaing screen
    Window.fill((back_color))
    Player = pygame.draw.rect(Window, light_color, [x_axis, y_axis, Block_size, Block_size])
    pygame.display.update()
0 голосов
/ 31 августа 2018

Вы получаете pygame.KEYDOWN только при первом нажатии клавиши, а не при ее удержании. Простое решение состоит в том, чтобы рисовать только когда клавиша нажата (т.е. когда x_int != 0)

#On Loop
while ON == True:
    #Screen Event
    for Screen in pygame.event.get():
        # <Removed not relevant code for brevity>
        #Player Movement K DOWN
        if Screen.type == pygame.KEYDOWN:
            if Screen.key == pygame.K_d:
                x_int = 20
            if Screen.key == pygame.K_a:
                x_int = -20
       #Player Movement K UP
        if Screen.type == pygame.KEYUP:
            if Screen.key == pygame.K_d or Screen.key == pygame.K_a:
                x_int = 0

    # Render only happens if x_int is not zero
    # (Need to add code to force render first time)
    if x_int:
        x_axis += x_int
        Window.fill((back_color))
        Player = pygame.draw.rect(Window, light_color, [x_axis, y_axis, Block_size, Block_size])
        pygame.display.update()

По мере того, как программа растет и усложняется, вам понадобится лучшая логика для отображения, но это поможет вам начать работу.

...