Reputation: 25
I would like the 'banana' to be shown when the space bar is pressed, while it follows the character movement, and then to be fired upon the release of the same.
import pygame
from pygame.locals import *
#inizializzazione
pygame.init()
screen=pygame.display.set_mode((400,750))
pygame.display.set_caption('MonkeyBanana')
FPS=60
#load image
img_ground = pygame.image.load('Surf/sfondo.jpg').convert_alpha()
surf_ground=pygame.transform.scale(img_ground,(img_ground.get_width(),screen.get_height()))
class Monkey (pygame.sprite.Sprite):
def __init__(self):
super().__init__()
self.sprites = [pygame.transform.scale((pygame.image.load('Surf/Animazioni/monkey_idle_00.png').convert_alpha()),
(screen.get_width() / 5, screen.get_height() / 7)),
pygame.transform.scale((pygame.image.load('Surf/Animazioni/monkey_idle_01.png').convert_alpha()),
(screen.get_width() / 5, screen.get_height() / 7)),
pygame.transform.scale((pygame.image.load('Surf/Animazioni/monkey_idle_02.png').convert_alpha()),
(screen.get_width() / 5, screen.get_height() / 7)),
pygame.transform.scale((pygame.image.load('Surf/Animazioni/monkey_idle_03.png').convert_alpha()),
(screen.get_width() / 5, screen.get_height() / 7))
]
self.launch_monkey=[]
for i in range(0, 19):
filename = "Surf/Animazioni/monkey_{:0>3}.png".format(i)
img = pygame.image.load(filename).convert_alpha()
img_reduced = pygame.transform.scale(img, (screen.get_width() / 5, screen.get_height() / 7))
self.launch_monkey.append(img_reduced)
self.count=0
self.count1 = 0
self.image = self.sprites[self.count]
self.rect = self.image.get_rect()
self.rect.midbottom = (screen.get_width() / 2, screen.get_height())
all_sprites.add(self)
def update(self):
self.count += 0.08
if self.count >= 3:
self.count = 0
self.image = self.sprites[int(self.count)]
if move_right and monkey.rect.right < screen.get_width():
monkey.rect.x += 5
elif move_left and monkey.rect.left > 0:
monkey.rect.x -= 5
def launch(self):
global launch
if launch:
self.count1 += 1
if self.count1 >= 19:
self.count1 = 0
launch = False
self.image = self.launch_monkey[int(self.count1)]
class Banana (pygame.sprite.Sprite):
def __init__(self):
super().__init__()
self.image= pygame.transform.scale((pygame.image.load('Surf/banana.png').convert_alpha()),
(screen.get_width() / 10, screen.get_height() / 15))
self.rect=self.image.get_rect()
self.rect.center = monkey.rect.center
all_banana.add(self)
here is the problem. Everything works fine on the first launch. The second time I press the space bar, the banana returns to the character's hands instead of continuing the run.
def update(self):
global new_banana
if keep_banana:
self.rect.center = monkey.rect.center
new_banana=False
if launch_banana:
self.rect.y -= 5
if self.rect.top<50:
self.kill()
#create sprite and Group
all_sprites = pygame.sprite.Group()
all_banana= pygame.sprite.Group()
monkey=Monkey()
#other variables
move_right=False
move_left=False
launch=False
launch_banana=False
keep_banana=False
new_banana=False
#principal cicle
done=False
while not done:
for ev in pygame.event.get():
if ev.type == QUIT:
done = True
if ev.type ==KEYDOWN:
if ev.key== K_RIGHT:
move_right=True
idle = False
if ev.key== K_LEFT:
move_left = True
idle = False
if ev.key==K_SPACE:
keep_banana = True
new_banana=True
elif ev.type ==KEYUP:
if ev.key== K_RIGHT:
move_right=False
idle = True
if ev.key== K_LEFT:
move_left=False
idle = True
if ev.key==K_SPACE:
launch_banana=True
keep_banana = False
launch = True
#Game logic
if new_banana:
banana=Banana()
#screen update
screen.blit(surf_ground, (0, 0))
all_sprites.draw(screen)
all_banana.draw(screen)
all_banana.update()
all_sprites.update()
monkey.launch()
pygame.display.flip()
pygame.time.Clock().tick(FPS)
#end principal cicle
pygame.quit()
It works to me in another version without classes,by adding the banana to a new group every time it is fired, but I can't get it to work on the classes. I have tried so many times, but nothing seems to work
Upvotes: 1
Views: 67
Reputation: 25
Thanks for the reply
So
implement the launch_banana= False in Space Keydown don't work:
if ev.key == K_SPACE:
launch_banana = False # <---
keep_banana = True
new_banana = True
I implemented the banana states in this way in the game logic and work fine, by creating 2 sprite group:
import pygame
from pygame.locals import *
#inizializzazione
pygame.init()
screen=pygame.display.set_mode((400,750))
pygame.display.set_caption('MonkeyBanana')
FPS=60
#load image
img_ground = pygame.image.load('Surf/sfondo.jpg').convert_alpha()
surf_ground=pygame.transform.scale(img_ground,(img_ground.get_width(),screen.get_height()))
class Monkey (pygame.sprite.Sprite):
[...]
class Banana(pygame.sprite.Sprite):
def __init__(self):
super().__init__()
self.image = pygame.transform.scale((pygame.image.load('Surf/banana.png').convert_alpha()),
(screen.get_width() / 10, screen.get_height() / 15))
self.rect = self.image.get_rect()
self.rect.center = monkey.rect.center
one_banana.add(self) <-------------GroupSingle
self.state = "keep"
def start(self):
self.state = "launched"
def update(self):
if self.state == "keep":
self.rect.center = monkey.rect.center
elif self.state == "launched":
self.rect.y -= 5
if self.rect.top < 50:
self.kill()
#create sprite and Group
all_sprites = pygame.sprite.Group()
all_banana= pygame.sprite.Group()
one_banana= pygame.sprite.GroupSingle() <------add this group
monkey=Monkey()
#other variables
move_right=False
move_left=False
launch=False
launch_banana=False
keep_banana=False
new_banana=False
#principal cicle
done=False
while not done:
for ev in pygame.event.get():
if ev.type == QUIT:
done = True
if ev.type ==KEYDOWN:
if ev.key== K_RIGHT:
move_right=True
idle = False
if ev.key== K_LEFT:
move_left = True
idle = False
if ev.key==K_SPACE:
keep_banana = True
new_banana=True
elif ev.type ==KEYUP:
if ev.key== K_RIGHT:
move_right=False
idle = True
if ev.key== K_LEFT:
move_left=False
idle = True
if ev.key==K_SPACE:
launch_banana=True
keep_banana = False
launch = True
#Game logic
**if new_banana:
banana=Banana()
if launch_banana:
one_banana.empty()
all_banana.add(banana) <------The new logic works
banana.start()
launch_banana=False
new_banana=False**
#screen update
screen.blit(surf_ground, (0, 0))
all_sprites.draw(screen)
all_banana.draw(screen)
one_banana.draw(screen)
one_banana.update()
all_banana.update()
all_sprites.update()
monkey.launch()
pygame.display.flip()
pygame.time.Clock().tick(FPS)
#end principal cicle
pygame.quit()
There is a way much simple to do this? Thank you in any case
Upvotes: 0
Reputation: 211230
launch_banana
makes the banana fly:
if launch_banana: self.rect.y -= 5
launch_banana
is False
at the beginning, but it is never set False
again once it has become True
. You have to set launch_banana
to False
when keep_banana
is set True
:
launch_banana=False
keep_banana=False
new_banana=False
# [...]
while not done:
for ev in pygame.event.get():
# [...]
if ev.type == KEYDOWN:
# [...]
if ev.key == K_SPACE:
launch_banana = False # <---
keep_banana = True
new_banana = True
elif ev.type == KEYUP:
# [...]
if ev.key == K_SPACE:
launch_banana = True
keep_banana = False
launch = True
Anyway, instead of all these Boolean variables, I propose to add a state to the Banana
class. The state can be "keep" at the beginning and can be changed to "launched" after the banana is started.
class Banana (pygame.sprite.Sprite):
def __init__(self):
super().__init__()
self.image= pygame.transform.scale((pygame.image.load('Surf/banana.png').convert_alpha()),
(screen.get_width() / 10, screen.get_height() / 15))
self.rect=self.image.get_rect()
self.rect.center = monkey.rect.center
all_banana.add(self)
self.state = "keep"
def start(self):
self.state = "launched"
def update(self):
if self.state == "keep":
self.rect.center = monkey.rect.center
elif self.state == "launched":
self.rect.y -= 5
if self.rect.top<50:
self.kill()
Upvotes: 1