Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Pygame - making a sprite move in the direction it is facing

I'm making a top down car racing game and I want to make the car rotate when you press the left and right keys (I’ve already done that part), the sprite's rotation is stored in a variable as degrees. I'd like to be able to make it move according to acceleration in the direction it is facing. I can figure out the acceleration part myself, it's just figuring out what pixel exactly is in that direction. Can anyone give me some simple code to help with this?

Here are the contents of the class that are relevant:

def __init__(self, groups):
    super(Car, self).__init__(groups)
    self.originalImage = pygame.image.load(os.path.join("Data", "Images", "Car.png")) #TODO Make dynamic
    self.originalImage.set_colorkey((0,255,0))
    self.image = self.originalImage.copy() # The variable that is changed whenever the car is rotated.

    self.originalRect = self.originalImage.get_rect() # This rect is ONLY for width and height, the x and y NEVER change from 0!
    self.rect = self.originalRect.copy() # This is the rect used to represent the actual rect of the image, it is used for the x and y of the image that is blitted.

    self.velocity = 0 # Current velocity in pixels per second
    self.acceleration = 1 # Pixels per second (Also applies as so called deceleration AKA friction)
    self.topSpeed = 30 # Max speed in pixels per second
    self.rotation = 0 # In degrees
    self.turnRate = 5 # In degrees per second

    self.moving = 0 # If 1: moving forward, if 0: stopping, if -1: moving backward


    self.centerRect = None

def update(self, lastFrame):
    if self.rotation >= 360: self.rotation = 0
    elif self.rotation < 0: self.rotation += 360

    if self.rotation > 0:
        self.image = pygame.transform.rotate(self.originalImage.copy(), self.rotation)
        self.rect.size = self.image.get_rect().size
        self.center() # Attempt to center on the last used rect

    if self.moving == 1:
        self.velocity += self.acceleration #TODO make time based

    if self.velocity > self.topSpeed: self.velocity = self.topSpeed # Cap the velocity
like image 456
JT Johnson Avatar asked Mar 18 '11 00:03

JT Johnson


People also ask

How do sprites work in Pygame?

The Pygame library has support for sprites. A sprite is a two dimensional image that is part of the larger graphical scene. Typically a sprite will be some kind of object in the scene that will be interacted with like a car, frog, or little plumber guy.

How do you rotate a player in Pygame?

To rotate the image we use the pygame. transform. rotate(image, degree) method where we pass the image that we are going to rotate and the degree by which rotation is to be done.

How do you know if a sprite is clicked pygame?

When you receive a mouse click event, you get the position by calling pygame. mouse. get_pos() . You can then check for a collision between a rect centered at the mouse position and your sprite's rect by calling pygame.


2 Answers

Trigonometry: The formula to get your coordinate is:

# cos and sin require radians
x = cos(radians) * offset
y = sin(radians) * offset

You use velocity for offset. (This means a negative velocity will drive backwards).

so:

def rad_to_offset(radians, offset): # insert better func name.
    x = cos(radians) * offset
    y = sin(radians) * offset
    return [x, y]

loop_update is something like:

# vel += accel
# pos += rad_to_offset( self.rotation, vel )

math.cos, math.sin: uses radians, so

storing rotations as radians is simpler. If you want to define speed / etc as degrees, you still can.

# store radians, but define as degrees
car.rotation_accel = radians(45)
car.rotation_max_accel = radians(90)
like image 53
ninMonkey Avatar answered Nov 03 '22 05:11

ninMonkey


I can't really do better than pointing you to this tutorial (*). In particular, the first part explains how to do rotation and make the sprites move in certain directions.


(*) Shameless plug :-) but very relevant to the question.

like image 40
Eli Bendersky Avatar answered Nov 03 '22 04:11

Eli Bendersky