Clemetron
Clemetron

Reputation: 37

Rotating an image in pygame so that it looks like its spinning

I am creating a game where the players attack is to spin 360 degrees. I have made it so it does do that however I get the problem of that it keeps going back to the original image every time it rotates. Any ideas on how to get it so that the images is constantly spinning

Here is a snippet of my code for the rotation:

self.rotate += 10
self.image_type = self.image
self.image = pygame.transform.rotate(self.image_type, self.rotate)

Update

Here is the majority of my code. My program is split into two parts; the main loop and the classes program

Code for my classes:

import pygame
from pygame import *
import random
import time
import math as maths
pygame.init()

class character(pygame.sprite.Sprite):
    def __init__(self):
        super().__init__()
        self.image1 = pygame.image.load("Knight_front.png").convert_alpha()
        self.image_type = self.image1
        self.image = self.image1
        self.rect = self.image.get_rect()
        self.rect.x, self.rect.y = 300,215
        self.st = 0
        self.dir = 0
        self.stab = False
        self.rotate = 0

    def update(self,keypress):
        self.prevx,self.prevy = self.rect.x,self.rect.y
        if keypress[K_w]:
            self.image = self.image_type
            self.rect.y -= 3
            self.dir = 0
        if keypress[K_s]:
            self.image = pygame.transform.rotate(self.image_type, 180)
            self.rect.y += 3
            self.dir = 180
        if keypress[K_a]:
            self.image = pygame.transform.rotate(self.image_type, 90)
            self.rect.x -= 3
            self.dir = 90
        if keypress[K_d]:
            self.image = pygame.transform.rotate(self.image_type, -90)
            self.rect.x += 3
            self.dir = -90
        if keypress[K_SPACE] and self.stab == False and time.time()>self.st+0.5:
            self.rotate += 10
            self.image_type = self.image
            self.image = pygame.transform.rotate(self.image_type, self.rotate)
            self.st = time.time()
            self.stab = True
        if time.time() > self.st + 0.25 and self.stab == True:
            self.image_type = self.image1
            self.image = pygame.transform.rotate(self.image_type, self.dir)
            self.stab = False
            if self.rotate == 360:
                self.rotate = 0

Code for my main loop:

import pygame
from pygame import *

width, height = 640, 480
screen = pygame.display.set_mode((width,height))#,FULLSCREEN)

from classes import *
import random

spriteList = pygame.sprite.Group()
player = character()
spriteList.add(player)


Clock = pygame.time.Clock()

    while True:

        keypress = pygame.key.get_pressed()
        screen.fill((255,255,255))
        spriteList.draw(screen)
        player.update(keypress)

        pygame.event.pump()
        Clock.tick(30)
        pygame.display.update()

        for event in pygame.event.get():
            if event.type == QUIT:
                pygame.quit()
                quit()
            if keypress[K_ESCAPE]:
                pygame.quit()

Upvotes: 1

Views: 507

Answers (2)

skrx
skrx

Reputation: 20438

I'd set the self.stab variable to True if the spacebar is pressed, then increment the angle (self.rotate), rotate the image and get a new rect each frame, and when 360 degrees are exceeded, reset the self.stab and self.rotate variables.

if keypress[K_SPACE]:
    self.stab = True

if self.stab:
    self.rotate += 10
    if self.rotate >= 360:
        self.rotate = 0
        self.stab = False
    # Rotate the image and get a new rect with the old center.
    self.image = pygame.transform.rotate(self.image_type, self.rotate)
    self.rect = self.image.get_rect(center=self.rect.center)

Upvotes: 1

Ethanol
Ethanol

Reputation: 370

Because of your short eexample, I can't give aa single correct solution. But I have some ideas.

My first idea is that you might have loaded self.image in a loop, which I doubt you did. If you ddd, simply move the loading of your image to the __init__() function of your class.

My second idea is that you define or assign your self.rotate variable to 0 in a loop, making it impossible to spin.

However, if you were to load the image outside of a loop, there is not much I can offer. I believe your given code is correct, but I can give you another way to do it.

class Thing:
    def __init__(self, location, image, rotate=0):
        self.image = image # has to be alreedy loaded and converted
        self.rotate =  rotate  # in case the instance wants a certain rotation when first drawn.
        self.loc = ocation
        self.rotated_image = pygame.transform.rotate(self.image, self.rotate)
    def spin_and_draw(self):
        rotate += 10
        self.rotated_image = pygame.tranform.rotate(self.image, self.rotate)
        screen.blit(self.rotated_image, (self.loc[0], self.loc[1]))

What I did was instead of assigningself.image_type to image and rotating self.image_type and then giving the results of thenrotation to self.image, I keptthe original image and then created a rotated image of it in another variable.

Upvotes: 0

Related Questions