【问题标题】:Moving a Sprite in the direction of an angle in Pygame [duplicate]在 Pygame 中沿角度方向移动 Sprite [重复]
【发布时间】:2018-02-16 18:18:01
【问题描述】:

我试图在 pygame 中沿角度方向移动精灵,使用左右箭头键来改变精灵的方向,但是当我按下向上键时,精灵只是向右移动。我有 2 个变量,它们采用速度和速度计算并将它们加在一起(vel_x 和 vel_y),然后我将它添加到精灵的位置(方向),但是当它向前移动时它不遵循精灵方向(如果 keybd_tupl[K_UP ])。

import pygame
import random
import math

from pygame.locals import *

window_wid = 800
window_hgt = 600

frame_rate = 50
delta_time = 1 / frame_rate
STATE_READY = 2

def game_loop_inputs():

    # look in the event queue for the quit event
    quit_ocrd = False
    for evnt in pygame.event.get():
        if evnt.type == QUIT:
            quit_ocrd = True

    return quit_ocrd

def game_loop_update(circle_hitbox):

    # start by assuming that no collisions have occurred
    circle_hitbox["col"] = False

    # return the new state of the rotating line and the circle hitbox
    return circle_hitbox


def game_loop_render(circle_hitbox, window_sfc):

    # clear the window surface (by filling it with black)
    window_sfc.fill( (0,0,0) )

    # draw the circle hitbox, in red if there has been a collision or in white otherwise
    if circle_hitbox["col"]:

        #pygame.draw.circle(window_sfc, (255, 0, 0), circle_hitbox["pos"], circle_hitbox["rad"])
        rotated_damage = pygame.transform.rotate(circle_hitbox["damage"], circle_hitbox["angle"])
        window_sfc.blit(rotated_damage, circle_hitbox["pos"])
    else:
        #pygame.draw.circle(window_sfc, (255, 255, 255), circle_hitbox["pos"], circle_hitbox["rad"])
        rotated_image = pygame.transform.rotate(circle_hitbox["sprite"], circle_hitbox["angle"])
        window_sfc.blit(rotated_image, circle_hitbox["pos"])

    # update the display
    pygame.display.update()


def main():

    # initialize pygame
    pygame.init()

    # create the window and set the caption of the window
    window_sfc = pygame.display.set_mode( (window_wid, window_hgt) )
    pygame.display.set_caption('"Toy" for the MDA Exercise')

    # create a clock
    clock = pygame.time.Clock()

    # this is the initial game state
    game_state = STATE_READY

#####################################################################################################
    # these are the initial game objects that are required (in some form) for the core mechanic provided
#####################################################################################################

    # this game object is a circulr
    circle_hitbox = {}
    circle_hitbox["pos"] = (window_wid // 2, window_hgt // 2)
    circle_hitbox["rad"] = 30
    circle_hitbox["col"] = False
    circle_hitbox["sprite"] = pygame.image.load("cars_racer_{}.png".format(random.randint(1, 3)))
    circle_hitbox["damage"] = pygame.image.load("cars_racer_red.png")
    circle_hitbox["crash"] = pygame.image.load("explosion.png")
    circle_hitbox["damaged"] = False
    circle_hitbox["angle"] = 0

    speed = 10.0
    vel_x = speed * math.cos(circle_hitbox["angle"] * (math.pi / 180))
    vel_y = speed * math.sin(circle_hitbox["angle"] * (math.pi / 180))

    # the game loop is a postcondition loop controlled using a Boolean flag
    closed_flag = False
    while not closed_flag:

    #####################################################################################################
        # this is the "inputs" phase of the game loop, where player input is retrieved and stored
    #####################################################################################################

        closed_flag = game_loop_inputs()

        keybd_tupl = pygame.key.get_pressed()
        if keybd_tupl[K_UP]:
            circle_hitbox["pos"] = (circle_hitbox["pos"][0] + vel_x, circle_hitbox["pos"][1] + vel_y)
            print(vel_y)
        if keybd_tupl[K_LEFT]:
            circle_hitbox["angle"] = (circle_hitbox["angle"] + 10.0)
        if keybd_tupl[K_RIGHT]:
            circle_hitbox["angle"] = (circle_hitbox["angle"] - 10.0)

    #####################################################################################################
        # this is the "update" phase of the game loop, where the changes to the game world are handled
    #####################################################################################################

        circle_hitbox = game_loop_update(circle_hitbox)

    #####################################################################################################
        # this is the "render" phase of the game loop, where a representation of the game world is displayed
    #####################################################################################################

        game_loop_render(circle_hitbox, window_sfc)

        # enforce the minimum frame rate
        clock.tick(frame_rate)

if __name__ == "__main__":
    main()

它只是不工作,我不知道为什么。

【问题讨论】:

  • 请将您的代码sn-p转成minimal, complete and verifiable example,这样我们就更容易理解和回答这个问题了。有关您的目标和问题的更多详细信息也会有所帮助。
  • @skrx 更新了我的人。

标签: pygame sprite python-3.6


【解决方案1】:

你必须在while循环中计算vel_xvel_y

while not closed_flag:
    closed_flag = game_loop_inputs()

    keybd_tupl = pygame.key.get_pressed()
    if keybd_tupl[K_UP]:
        circle_hitbox["pos"] = (circle_hitbox["pos"][0] + vel_x, circle_hitbox["pos"][1] + vel_y)
        print(vel_y)
    if keybd_tupl[K_LEFT]:
        circle_hitbox["angle"] -= 1.0
    if keybd_tupl[K_RIGHT]:
        circle_hitbox["angle"] += 1.0

    # `math.radians` can be used instead of `* (math.pi / 180)`
    vel_x = speed * math.cos(math.radians(circle_hitbox["angle"]))
    vel_y = speed * math.sin(math.radians(circle_hitbox["angle"]))

另外,在game_loop_render 函数中将负角传递给pygame.transform.rotate

rotated_damage = pygame.transform.rotate(circle_hitbox["damage"], -circle_hitbox["angle"])

旋转可能看起来仍然不正确(我正在使用一些替换图像,但它们没有正确旋转)。如果您想知道如何在 pygame 中围绕其中心旋转 pygame 精灵和图像,请查看 this answer

【讨论】:

  • 谢谢,您对轮换的看法是对的,但我会弄清楚的!
猜你喜欢
  • 2014-05-13
  • 1970-01-01
  • 2019-05-09
  • 2019-05-09
  • 1970-01-01
  • 2015-01-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多