Display a power indicator above the player head

Hello and it has been a very long time I am not posting anything on this website and today I am just going to finish up the unfinished business from the previous python project, which is to display a power indicator above the player head to show that the player is in full power after he has eaten the mana during the game, if he collides with the enemy then that power will be used up and the power indicator will disappear. I am using the self.weak switch to indicate whether the player has eaten a mana or is he collides with an enemy. In this example, we will only edit one file, which is the boy sprite class.

from BoyObject import BoyObject
from pygame import math as mt
from pygame.locals import *
from GameSprite import GameSprite
import pygame

class BoySprite(object):

    def __init__(self, scene, level, enemy_manager, mana_manager, level_manager, score_manager):

        self.row = 10
        self.column = 10
        self.scene = scene # game scene instance
        self.space = 64 # image width and height
        self.level = level # current game level
        self.enemy_manager = enemy_manager # the reference of enemy manager
        self.mana_manager = mana_manager # the reference of mana manager
        self.score_manager = score_manager # the reference of score manager
        self.WIDTH = 640
        self.level_manager = level_manager
        self.prepare_boy(self.level)

    def prepare_boy(self, level):
        self.boy_object = BoyObject()
        self.boy_object_list = self.boy_object.get_object_list(level)
        self.boy_original_position = self.boy_object.get_original_position(level)
        self.x = self.boy_original_position[0]
        self.y = self.boy_original_position[1]
        self.speed = 2
        self.boy_image_sprite_right = 'Asset/bright.png'
        self.boy_image_sprite_left = 'Asset/bleft.png'
        self.boy_sprite = self.boy_image_sprite_right
        self.frame = 3
        self.up = False
        self.ladder = False
        self.left = False
        self.weak = False
        self.boy_rect = Rect(self.frame * 64, 0, 64, 64)
        self.sprite_boy = GameSprite(self.boy_sprite, self.boy_rect)
        self.boy_surface = self.sprite_boy.getImage()
        self.boy_ladder_list = self.boy_object.get_object_boundary(level)
        self.boy_bottom_boundary_list = self.boy_object.get_object_bottom_boundary(level)
        self.boy_side_boundary_list = self.boy_object.get_object_side_boundary(level)
        self.boy_door_boundary_list = self.boy_object.get_object_door_boundary(level)
        self.enemy_list = self.enemy_manager.get_enemy_list()
        self.mana_list = self.mana_manager.get_mana_list()
        self.life = 1
        self.initialize()

    # set the x and the y direction for the player object

    def setX(self, x):

        if(self.ladder == True):
            return
        self.x += x
        if (self.up == True and x < 0):
            self.frame = 1
            self.up = False
        elif(self.up == True and x > 0):
            self.frame = 0
            self.up = False
        if(x < 0):
            self.left = True
            self.frame += 1
            if (self.frame > 5):
                self.frame = 1
            self.boy_sprite = self.boy_image_sprite_left
        elif(x > 0):
            self.frame += 1
            self.left = False
            if (self.frame > 4):
                self.frame = 0
            self.boy_sprite = self.boy_image_sprite_right
        elif(x == 0):
            if(self.left == True):
                self.frame = 2
                self.boy_sprite = self.boy_image_sprite_left
            elif(self.left == False):
                self.frame = 3
                self.boy_sprite = self.boy_image_sprite_right
        self.boy_rect = Rect(self.frame * 64, 0, 64, 64)
        self.sprite_boy = GameSprite(self.boy_sprite, self.boy_rect)
        self.boy_surface = self.sprite_boy.getImage()

    def setY(self, y):

        self.boy_rect = Rect(self.x, self.y+y, 64, 64)
        if(self.isUpDown(self.boy_rect, y) == True):
            self.y += y
        if(y == 0):
            self.frame = 9
        elif(self.up == False):
            self.frame = 6
            self.up = True
        else:
            if(y < 0):
                self.frame -= 1
            elif(y > 0):
                self.frame += 1
            if(self.frame > 10):
                self.frame = 6
            elif(self.frame < 6):
                self.frame += 2
        self.boy_sprite = self.boy_image_sprite_right
        self.boy_rect = Rect(self.frame * 64, 0, 64, 64)
        self.sprite_boy = GameSprite(self.boy_sprite, self.boy_rect)
        self.boy_surface = self.sprite_boy.getImage()

    def checkboundary(self):

        if(self.x < 0):
            self.x = 0
        elif(self.x > self.WIDTH - self.space):
            self.x = self.WIDTH - self.space
        else:
            self.isLeftRight()

    def isUpDown(self, rect, y):

        for boundary in self.boy_ladder_list:
            boundary_rect = Rect(boundary[0], boundary[1], 64, 64)
            if ((boundary_rect.collidepoint(self.x, self.y+y) == True or boundary_rect.collidepoint(self.x, self.y+self.space+y) == True) and (self.x % self.space == 0)):
                for boundary_bottom in self.boy_bottom_boundary_list:
                    boundary_rect = Rect(boundary_bottom[0], boundary_bottom[1], 64, 64)
                    if (boundary_rect.colliderect(rect) == True):
                        self.ladder = False
                        return False
                self.ladder = True
                return True
        self.ladder = False
        return False

    def isLeftRight(self):

        for boundary in self.boy_side_boundary_list:
            boundary_rect = Rect(boundary[0], boundary[1], 64, 64)
            boy_rect = Rect(self.x, self.y, 64, 64)
            if (boundary_rect.colliderect(boy_rect) == True):
                if(self.left == True):
                    self.x += self.speed
                else:
                    self.x -= self.speed

    def update(self):

        self.checkboundary()
        self.check_mana_collide()
        self.check_collide()
        self.check_win()
        self.move_boy()

    def check_win(self):
        for door in self.boy_door_boundary_list:
            if(door[0] == self.x and door[1] == self.y):
                self.level_manager.increase_level()

    def check_collide(self):
        for enemy in self.enemy_list:
            enemy_rect = Rect(enemy.x, enemy.y, 64, 64)
            boy_rect = Rect(self.x, self.y, 64, 64)

            if (enemy_rect.colliderect(boy_rect) == True and enemy.alive == True):
                if(self.life <= 0):
                    self.level_manager.reset_level()
                    return
                else:
                    self.life -= 1
                    self.score_manager.set_score(-50)
                    enemy.alive = False
                    self.weak = False

    def check_mana_collide(self):
        for mana in self.mana_list:
            mana_rect = Rect(mana.x, mana.y, 64, 64)
            if (mana_rect.collidepoint(self.x, self.y) == True and mana.alive == True):
                self.life += 1
                self.weak = True
                self.score_manager.set_score(+50)
                mana.alive = False
                return

    def move_boy(self):
        self.draw_pos = mt.Vector2(self.x, self.y)  # the position of the image on game scene

    def initialize(self):
        for row in range(self.row):
            for column in range(self.column):

                if(self.boy_object_list[row][column] == 1):

                    self.draw_pos = mt.Vector2(self.x, self.y)  # the vector position of the image on game scene
                    self.scene.blit(self.boy_surface, self.draw_pos)  # draw enemy frame

    def draw(self):
        self.scene.blit(self.boy_surface, self.draw_pos)  # draw boy frame
        if(self.weak == True):
            pygame.draw.rect(self.scene, Color(0, 0, 225, 0), Rect(self.x+12, self.y-10, 10, 10), False)

If we run the above program again then we will see the following outcome.

With that, we have finally concluded the 2 months long project which costs me around 1000 hours of hard work and we will now looking forward to a new chapter of the game development, as I have mentioned before, we will create a new pygame project in the coming future. If you want to help this site out, kindly do consider to donate to this website, thank you in advance!

Online Game Manual and Sound On Off

Hello and in this chapter, we will wrap up the features on the main manual page so we can move on to the last feature on the game page which is the power bar display.

We will edit two files to finish up the final two features on the manual page. The first one is to create a clickable game manual button which when someone clicks on it will open up an online manual page. The second feature is a sound button which when someone clicks on it will either play the game music or mute the game music.

The first file is the start scene class where two buttons will be created. The sound button will display either the mute button or the sound on button depends on whether the music has been muted or not. The manual button will load the online menu page after it has been clicke by the player.

from BgSprite import BgSprite
from GameSprite import GameSprite
from pygame.locals import *
from pygame import math as mt
import pygame
import pygame.font as txt
from AirStrikeColor import AirStrikeColor

class StartScene(object):

    def __init__(self, scene, lm):

        self.level_manager = lm

        self.scene = scene
        self.play_button = 'Asset/play.png'
        self.about_button  = 'Asset/about.png'
        self.exit_button = 'Asset/exit.png'
        self.scene_button = 'Asset/scene.png'
        self.score_button = 'Asset/score.png'
        self.home_button = 'Asset/back.png'
        self.button_image = 'Asset/button_play.png'
        self.manual_button = 'Asset/manual.png'
        self.bg_image = 'Asset/start.png'
        self.win_image = 'Asset/winn.png'
        self.general_image = 'Asset/general.png'


        self.soundon = 'Asset/sound.png'
        self.soundoff = 'Asset/soundoff.png'
        self.home_button_image = 'Asset/home.png'
        self.game_logo = 'Asset/enemy3.png'
        self.bg_rect = Rect(0, 0, 660, 660)
        self.button_rect = Rect(0, 0,  306, 112)
        self.home_button_rect = Rect(0, 0, 200, 53)
        self.back_button_rect = Rect(0, 0, 40, 30)
        self.sound_button_rect = Rect(0, 0, 30, 30)
        self.game_logo_rect = Rect(0, 0, 160, 160)

        self.sprite = BgSprite(self.general_image, self.bg_rect)


        self.sprite_win = BgSprite(self.win_image, self.bg_rect)

        self.sprite_pause = BgSprite(self.general_image, self.bg_rect)

        self.soundon_button = GameSprite(self.soundon, self.sound_button_rect)
        self.soundoff_button = GameSprite(self.soundoff, self.sound_button_rect)

        self.soundoff_button_surface = self.soundoff_button.getImage()  # get the button sprite surface
        self.soundon_button_surface = self.soundon_button.getImage()  # get the button sprite surface
        self.game_logo_sprite = GameSprite(self.game_logo, self.game_logo_rect)
        self.sprite_button = GameSprite(self.button_image, self.button_rect)
        self.sprite_home_pause_button = GameSprite(self.home_button_image, self.home_button_rect)
        self.sprite_scene_button = GameSprite(self.scene_button, self.home_button_rect)
        self.sprite_manual_button = GameSprite(self.manual_button, self.home_button_rect)
        self.sprite_exit_button = GameSprite(self.exit_button, self.home_button_rect)
        self.sprite_play_button = GameSprite(self.play_button, self.home_button_rect)
        self.sprite_about_button = GameSprite(self.about_button, self.home_button_rect)
        self.sprite_score_button = GameSprite(self.score_button, self.home_button_rect)
        self.sprite_home_button = GameSprite(self.home_button, self.back_button_rect)


        self.win_surface = self.sprite_win.getImage()  # get the win sprite surface
        self.pause_surface = self.sprite_pause.getImage()  # get the pause sprite surface
        self.surface = self.sprite.getImage()  # get the start scene sprite surface
        self.button_surface = self.sprite_button.getImage() # get the button sprite surface
        self.home_pause_button_surface = self.sprite_home_pause_button.getImage() # get the button sprite surface
        self.play_button_surface = self.sprite_play_button.getImage()  # get the button sprite surface
        self.about_button_surface = self.sprite_about_button.getImage()  # get the button sprite surface
        self.score_button_surface = self.sprite_score_button.getImage()  # get the button sprite surface
        self.manual_button_surface = self.sprite_manual_button.getImage()  # get the button sprite surface
        self.scene_button_surface = self.sprite_scene_button.getImage()  # get the button sprite surface
        self.home_button_surface = self.sprite_home_button.getImage()  # get the button sprite surface
        self.exit_button_surface = self.sprite_exit_button.getImage()  # get the button sprite surface
        self.game_logo_surface = self.game_logo_sprite.getImage() # get game logo image
        self.draw_pos = mt.Vector2(0, 0)
        self.draw_button_pos = mt.Vector2(177, 274)
        self.draw_game_logo_pos = mt.Vector2(249, 100)
        self.draw_play_button_pos = mt.Vector2(229, 200)
        self.draw_about_button_pos = mt.Vector2(229, 263)
        self.draw_home_button_pos = mt.Vector2(229, 263)
        self.draw_score_button_pos = mt.Vector2(229, 328)
        self.draw_manual_button_pos = mt.Vector2(229, 393)
        self.draw_exit_button_pos = mt.Vector2(229, 456)
        self.draw_scene_button_pos = mt.Vector2(229, 519)
        self.draw_back_button_pos = mt.Vector2(10, 620)

        self.draw_sound_button_pos = mt.Vector2(10, 620)

        self.soundon = True
        self.count = 0

        self.font = txt.Font('Asset/ft.ttf', 90)
        self.credit_font = txt.Font('Asset/ft.ttf', 50)
        self.score_text = "Top Achievements"
        self.credit_text_i = "Create by : IslandTropicalMan"
        self.over_text_i = "Game Over"
        self.next_text_i = "Next Level"
        self.text_width, self.text_height = self.font.size(self.score_text)
        self.credit_text_width, self.credit_text_height = self.credit_font.size(self.credit_text_i)
        self.over_text_width, self.over_text_height = self.credit_font.size(self.over_text_i)
        self.next_text_width, self.next_text_height = self.credit_font.size(self.next_text_i)
        self.x_title = 330 - self.text_width/2
        self.x_credit = 330 - self.credit_text_width/2
        self.x_over = 330 - self.over_text_width / 2
        self.x_next = 330 - self.next_text_width/2
        self.y_title = 60
        self.title_rect = Rect(self.x_title, self.y_title, self.text_width, self.text_height)
        self.title_score_text = self.font.render(self.score_text, 1, (255, 255, 255))
        self.credit_rect = Rect(self.x_credit, 300, self.credit_text_width, self.credit_text_height)
        self.over_rect = Rect(self.x_over, 190, self.over_text_width, self.over_text_height)
        self.next_rect = Rect(self.x_next, 190, self.next_text_width, self.next_text_height)
        self.credit_text = self.credit_font.render(self.credit_text_i, 1, (255, 255, 255))
        self.over_text = self.credit_font.render(self.over_text_i, 1, (255, 255, 255))
        self.next_text = self.credit_font.render(self.next_text_i, 1, (255, 255, 255))
        self.score_value_text = ''
        self.f1 = None
        self.font1 = txt.Font('Asset/ft.ttf', 100)
        self.score_rect = Rect(100, self.y_title+self.text_height, 100, 100)
        self.home_background_color = AirStrikeColor(0, 0, 0, 255)

    def draw(self, state):

        if(state == 0):
            self.scene.fill(self.home_background_color)
            self.scene.blit(self.game_logo_surface, self.draw_game_logo_pos) # draw a game logo
            self.scene.blit(self.play_button_surface, self.draw_play_button_pos)  # draw a button sprite
            self.scene.blit(self.about_button_surface, self.draw_about_button_pos)  # draw a button sprite
            self.scene.blit(self.score_button_surface, self.draw_score_button_pos)  # draw a button sprite
            self.scene.blit(self.manual_button_surface, self.draw_manual_button_pos)  # draw a button sprite
            self.scene.blit(self.exit_button_surface, self.draw_exit_button_pos)  # draw a button sprite
            self.scene.blit(self.scene_button_surface, self.draw_scene_button_pos)  # draw a button sprite
            if(self.soundon == True):
                self.scene.blit(self.soundon_button_surface, self.draw_sound_button_pos)  # draw a button sprite
            else:
                self.scene.blit(self.soundoff_button_surface, self.draw_sound_button_pos)  # draw a button sprite
        elif(state == 2):

            self.scene.fill(self.home_background_color)
            self.scene.blit(self.over_text, self.over_rect)  # the over text

        elif (state == 3):

            self.scene.fill(self.home_background_color)
            self.scene.blit(self.next_text, self.next_rect)  # the next text

        elif(state == 4):
            self.scene.blit(self.win_surface, self.draw_pos)  # draw a win sprite

        elif (state == 5):
            self.scene.fill(self.home_background_color) # draw a background
            self.scene.blit(self.credit_text, self.credit_rect)  # the credit text
            #self.scene.blit(self.about_surface, self.draw_pos)  # draw a about sprite
            self.scene.blit(self.home_button_surface, self.draw_back_button_pos)  # draw a button sprite

        elif (state == 6):
            self.scene.blit(self.manual_surface, self.draw_pos)  # draw a manual sprite
            self.scene.blit(self.home_button_surface, self.draw_back_button_pos)  # draw a button sprite

        elif (state == 7):
            #self.scene.blit(self.pause_surface, self.draw_pos)  # draw a pause sprite
            self.scene.fill(self.home_background_color)  # draw a background
            self.scene.blit(self.play_button_surface, self.draw_play_button_pos)  # draw a button sprite
            self.scene.blit(self.home_pause_button_surface, self.draw_home_button_pos)  # draw a button sprite

        elif (state == 8):

            self.scene.fill(self.home_background_color)  # draw a background
            self.scene.blit(self.title_score_text, self.title_rect) # the score title first
            list_level = self.level_manager.get_list()

            for i in range(len(list_level)):
                self.score_rect = Rect(95, self.y_title + self.text_height + self.count * 100, 100, 100)
                self.score_value_text = str(self.count+1) + ".) Level " + str(list_level[i])
                self.value_score_text = self.font1.render(self.score_value_text, 1, (255, 255, 255))
                self.scene.blit(self.value_score_text, self.score_rect)  # the top 5 levels of the game
                self.count += 1

            self.count = 0

            self.scene.blit(self.home_button_surface, self.draw_back_button_pos)  # draw a button sprite

        if(state == 2 or state == 3 or state == 4):
            self.scene.blit(self.button_surface, self.draw_button_pos)  # draw a button sprite

        pygame.display.flip()

The final file we need to edit is the game manager class and I will leave you to study the mechanism to trigger the above mentioned features by yourself.

from Player import Player
from Background import Background
from EnemyManager import EnemyManager
from Overlap import Overlap
from ExplosionManager import ExplosionManager
from Score import Score
from StartScene import StartScene
from pygame.locals import *
from LevelManager import LevelManager
import pygame
import webbrowser
from Scene import Scene

class GameManager(object):

    def __init__(self, scene):

        self.scene = scene

        self.load_music()
        self.play_music()
        self.overlap_manager = Overlap()
        self.level_manager = LevelManager(self)
        self.level_manager.set_level()
        self.setup(self.level_manager.get_level())
        self.start_scene = StartScene(scene, self.level_manager)
        #self.setup(3)

        self.pause = False # flag to pause the game

        self.game_scene = Scene(self.scene)

        #game state
        self.LOAD = 0
        self.GAME = 1
        self.OVER = 2
        self.NEXT = 3
        self.WIN = 4
        self.ABOUT = 5
        self.MANUAL = 6
        self.PAUSE = 7
        self.SCORE = 8
        self.SCENE = 9

        self.state = self.LOAD

    def setup(self, game_level):

        self.game_level = game_level
        self.score_manager = Score(self.scene, self.level_manager)
        self.background = Background(self.scene)
        self.player = Player(self.scene)
        self.enemy_manager = EnemyManager(self.scene, self.player, game_level)
        self.explosion_manager = ExplosionManager(self.scene)

    def loop(self):

        if(self.state == self.LOAD):
            self.start_scene.draw(self.state)
        elif(self.state == self.OVER or self.state == self.NEXT or self.state == self.WIN or self.state == self.ABOUT or self.state == self.MANUAL or self.state == self.SCORE):
            self.start_scene.draw(self.state)
        elif(self.state == self.SCENE):
            self.game_scene.draw()
        elif(self.state == self.GAME):

            self.update()
            self.draw()

        elif(self.state == self.PAUSE):

            self.start_scene.draw(self.state)

    def isAreaClick(self, x, y):
        if (self.state == self.LOAD or self.state == self.OVER or self.state == self.NEXT or self.state == self.WIN or self.state == self.ABOUT or self.state == self.SCORE or self.state == self.SCENE or self.state == self.MANUAL or self.state == self.PAUSE):
            self.rect = Rect(177, 274, 306, 112) # the position of the play button on the scene
            self.rect_play = Rect(229, 200, 200, 53)  # the position of the play button on the home scene
            self.rect_about = Rect(229, 263, 200, 53)  # the position of the about button on the home scene
            #self.rect_exit = Rect(229, 456, 200, 53)  # the position of the exit button on the home scene
            self.rect_pause_home = Rect(229, 263, 200, 53)  # the position of the home button on pause scene
            self.rect_score = Rect(229, 328, 200, 53)  # the position of the score button on the home scene
            self.rect_manual = Rect(229, 393, 200, 53)  # the position of the manual button on the home scene
            self.rect_scene = Rect(229, 519, 200, 53)  # the position of the manual button on the home scene
            self.rect_back = Rect(10, 620, 40, 30)  # the position of the back button on the home scene
            self.rect_sound = Rect(10, 620, 30, 30) # the position of the sound button on the home scene
            self.rect_scene_next = Rect(610, 330, 30, 30)  # the position of the next scene button on scene
            self.rect_scene_previous = Rect(50, 330, 30, 30)  # the position of the previous scene button on scene

            if(self.rect.collidepoint(x, y) and (self.state == self.OVER or self.state == self.NEXT or self.state == self.WIN)):
                self.state = self.GAME
            elif(self.rect_play.collidepoint(x,y) and self.state == self.LOAD):
                self.state = self.GAME
            elif (self.rect_play.collidepoint(x, y) and self.state == self.PAUSE):
                self.state = self.GAME
            elif (self.rect_about.collidepoint(x, y) and self.state == self.LOAD):
                self.state = self.ABOUT
            elif (self.rect_score.collidepoint(x, y) and self.state == self.LOAD):
                self.state = self.SCORE
            elif (self.rect_scene.collidepoint(x, y) and self.state == self.LOAD):
                self.state = self.SCENE
            elif (self.rect_back.collidepoint(x, y) and self.state == self.SCENE):
                self.state = self.LOAD
            elif (self.rect_scene_next.collidepoint(x, y) and self.state == self.SCENE):
                self.game_scene.set_next_image()
            elif (self.rect_scene_previous.collidepoint(x, y) and self.state == self.SCENE):
                self.game_scene.set_previous_image()
            elif (self.rect_pause_home.collidepoint(x, y) and self.state == self.PAUSE):

                self.state = self.LOAD
                self.setup(self.level_manager.get_level())
                self.save_level()

            elif (self.rect_manual.collidepoint(x, y) and self.state == self.LOAD):
                webbrowser.open_new('http://gamingdirectional.com/blog/2018/12/25/air-strike//')
            elif (self.rect_back.collidepoint(x, y) and (self.state == self.ABOUT or self.state == self.MANUAL or self.state == self.SCORE)):
                self.state = self.LOAD
            elif (self.rect_sound.collidepoint(x, y) and self.state == self.LOAD):

                if(self.start_scene.soundon == True):
                    self.start_scene.soundon = False
                    pygame.mixer_music.pause()
                else:
                    self.start_scene.soundon = True
                    pygame.mixer_music.unpause()

    def save_level(self):
       self.level_manager.save_level()

    def set_pause(self, pause):

        self.pause = pause

        if(self.pause == True):

            self.state = self.PAUSE

    def load_music(self):
        pygame.mixer_music.load('Music/winternight.ogg')

    def play_music(self):
        pygame.mixer_music.play(-1) #play the music infinite time

    def set_player_x(self, _x):
        if (self.state == self.GAME):
            self.player.setX(_x)

    def save_scene(self):
        self.game_scene.take_screen()

    def set_player_y(self, _y):
        if (self.state == self.GAME):
            self.player.setY(_y)

    def set_missile_strike(self, strike):
        if (self.state == self.GAME):
            self.player.setStrike(strike)

    def update(self):
        self.player.update()
        self.enemy_manager.update()
        self.isOverlap()
        self.explosion_manager.explosion_update()

    # check for player, enemy, missiles overlap
    def isOverlap(self):
        self.overlap_manager.isOverlap(self.player, self.enemy_manager, self.explosion_manager, self.score_manager, self)

    def draw(self):
        if(self.state == self.GAME):
            self.background.draw()
            self.player.draw()
            self.enemy_manager.draw()
            self.explosion_manager.draw()
            self.score_manager.draw()
            pygame.display.flip()

In the next chapter we will tune up the final part of the project which is to display the power bar on the game scene.

Exit the game on the main menu page or during the game stage

In this chapter we will edit the main file of the pygame project so when we click on the ‘x’ button on the top right of the game window during the game stage or we click on the exit button on the main menu page, the current game level will be saved and the game will exit. The position of the exit button on the start scene class remains unchanged so the only file we need to edit is the main file where we will create an exit button rectangle which will be used to determine whether the exit button has been clicked or not, if so then the game will exit. Or else if the ‘x’ button has been clicked then the game will exit as well.

import pygame
from pygame.locals import *
from GameManager import GameManager

pygame.init()

size = width, height = 640, 640
pygame.display.set_caption("Amaze Boy")  # set the title of the window
screen = pygame.display.set_mode(size)
game_manager = GameManager(screen)
rect_exit = Rect(229, 456, 200, 53)  # the position of the exit button on the home scene
running = True
pygame.key.set_repeat(100, 40)

while running:

    for event in pygame.event.get():
        # when the user clicks on the 'x'
        if event.type == pygame.QUIT:
            game_manager.save_level()
            running = False

        # detect key press event
        if event.type == KEYDOWN:

            if (game_manager.state == 1):

                if event.key == K_LEFT:
                    game_manager.set_player_x(-2)
                elif event.key == K_RIGHT:
                    game_manager.set_player_x(2)
                elif event.key == K_UP:
                    game_manager.set_player_y(-2)
                elif event.key == K_DOWN:
                    game_manager.set_player_y(2)

        elif event.type == KEYUP:

            if (game_manager.state == 1):

                if event.key == K_LEFT:
                    game_manager.set_player_x(0)
                elif event.key == K_RIGHT:
                    game_manager.set_player_x(0)
                elif event.key == K_UP:
                    game_manager.set_player_y(0)
                elif event.key == K_DOWN:
                    game_manager.set_player_y(0)
                elif event.key == K_p:
                    game_manager.set_pause(True)  # set the pause state to true
                elif event.key == K_s: # take the game screenshot
                    game_manager.save_scene()

        elif event.type == pygame.MOUSEBUTTONDOWN:
            x, y = event.pos
            if (rect_exit.collidepoint(x, y) and game_manager.state == game_manager.LOAD):
                game_manager.save_level()
                running = False
            # 1 is the left mouse button
            elif event.button == 1:
                game_manager.isAreaClick(x, y)

    game_manager.loop()

We have already included the code of the save_level method of the game manager class in the previous chapter so we will not show that same code again in this chapter. Here is the final outcome.

Like, share or follow me on Twitter.

Touch up the about scene

Hello and welcome back, in the next few chapters we will touch up all the game scenes one by one for our new pygame project. In this chapter, we will touch up the About scene where we will adjust the position of the credit text accordingly. We will only need to edit one file and that is the start scene class in order to touch up the about scene.

from BgSprite import BgSprite
from GameSprite import GameSprite
from pygame.locals import *
from pygame import math as mt
import pygame
import pygame.font as txt
from AmazeboyColor import AmazeboyColor

class StartScene(object):

    def __init__(self, scene, lm):

        self.level_manager = lm

        self.scene = scene
        self.play_button = 'Asset/play.png'
        self.about_button  = 'Asset/about.png'
        self.exit_button = 'Asset/exit.png'
        self.scene_button = 'Asset/scene.png'
        self.score_button = 'Asset/score.png'
        self.home_button = 'Asset/back.png'
        self.button_image = 'Asset/button_play.png'
        self.manual_button = 'Asset/manual.png'
        self.bg_image = 'Asset/start.png'
        self.win_image = 'Asset/winn.png'
        self.general_image = 'Asset/general.png'

        self.soundon = 'Asset/sound.png'
        self.soundoff = 'Asset/soundoff.png'
        self.home_button_image = 'Asset/home.png'
        self.game_logo = 'Asset/menu.png'
        self.bg_rect = Rect(0, 0, 640, 640)
        self.button_rect = Rect(0, 0,  306, 112)
        self.home_button_rect = Rect(0, 0, 200, 53)
        self.back_button_rect = Rect(0, 0, 40, 30)
        self.sound_button_rect = Rect(0, 0, 30, 30)

        self.animated_count = 0
        #self.game_logo_rect = Rect(self.animated_count*550, 0, 550, 550)

        self.sprite = BgSprite(self.general_image, self.bg_rect)


        self.sprite_win = BgSprite(self.win_image, self.bg_rect)

        self.sprite_pause = BgSprite(self.general_image, self.bg_rect)

        self.soundon_button = GameSprite(self.soundon, self.sound_button_rect)
        self.soundoff_button = GameSprite(self.soundoff, self.sound_button_rect)

        self.soundoff_button_surface = self.soundoff_button.getImage()  # get the button sprite surface
        self.soundon_button_surface = self.soundon_button.getImage()  # get the button sprite surface
        #self.game_logo_sprite = GameSprite(self.game_logo, self.game_logo_rect)
        self.sprite_button = GameSprite(self.button_image, self.button_rect)
        self.sprite_home_pause_button = GameSprite(self.home_button_image, self.home_button_rect)
        self.sprite_scene_button = GameSprite(self.scene_button, self.home_button_rect)
        self.sprite_manual_button = GameSprite(self.manual_button, self.home_button_rect)
        self.sprite_exit_button = GameSprite(self.exit_button, self.home_button_rect)
        self.sprite_play_button = GameSprite(self.play_button, self.home_button_rect)
        self.sprite_about_button = GameSprite(self.about_button, self.home_button_rect)
        self.sprite_score_button = GameSprite(self.score_button, self.home_button_rect)
        self.sprite_home_button = GameSprite(self.home_button, self.back_button_rect)

        self.win_surface = self.sprite_win.getImage()  # get the win sprite surface
        self.pause_surface = self.sprite_pause.getImage()  # get the pause sprite surface
        self.surface = self.sprite.getImage()  # get the start scene sprite surface
        self.button_surface = self.sprite_button.getImage() # get the button sprite surface
        self.home_pause_button_surface = self.sprite_home_pause_button.getImage() # get the button sprite surface
        self.play_button_surface = self.sprite_play_button.getImage()  # get the button sprite surface
        self.about_button_surface = self.sprite_about_button.getImage()  # get the button sprite surface
        self.score_button_surface = self.sprite_score_button.getImage()  # get the button sprite surface
        self.manual_button_surface = self.sprite_manual_button.getImage()  # get the button sprite surface
        self.scene_button_surface = self.sprite_scene_button.getImage()  # get the button sprite surface
        self.home_button_surface = self.sprite_home_button.getImage()  # get the button sprite surface
        self.exit_button_surface = self.sprite_exit_button.getImage()  # get the button sprite surface
        #self.game_logo_surface = self.game_logo_sprite.getImage() # get game logo image
        self.draw_pos = mt.Vector2(0, 0)
        self.draw_button_pos = mt.Vector2(177, 274)
        self.draw_game_logo_pos = mt.Vector2(170, 103)
        self.draw_play_button_pos = mt.Vector2(229, 200)
        self.draw_about_button_pos = mt.Vector2(229, 263)
        self.draw_home_button_pos = mt.Vector2(229, 263)
        self.draw_score_button_pos = mt.Vector2(229, 328)
        self.draw_manual_button_pos = mt.Vector2(229, 393)
        self.draw_exit_button_pos = mt.Vector2(229, 456)
        self.draw_scene_button_pos = mt.Vector2(229, 519)
        self.draw_back_button_pos = mt.Vector2(10, 590)

        self.draw_sound_button_pos = mt.Vector2(10, 600)

        self.soundon = True
        self.count = 0

        self.font = txt.Font('Asset/ft.ttf', 90)
        self.credit_font = txt.Font('Asset/ft.ttf', 50)
        self.score_text = "Top Achievements"
        self.credit_text_i = "Create by : IslandTropicalMan"
        self.over_text_i = "Game Over"
        self.next_text_i = "Next Level"
        self.text_width, self.text_height = self.font.size(self.score_text)
        self.credit_text_width, self.credit_text_height = self.credit_font.size(self.credit_text_i)
        self.over_text_width, self.over_text_height = self.credit_font.size(self.over_text_i)
        self.next_text_width, self.next_text_height = self.credit_font.size(self.next_text_i)
        self.x_title = 330 - self.text_width/2
        self.x_credit = 330 - self.credit_text_width/2
        self.x_over = 330 - self.over_text_width / 2
        self.x_next = 330 - self.next_text_width/2
        self.y_title = 30
        self.title_rect = Rect(self.x_title, self.y_title, self.text_width, self.text_height)
        self.title_score_text = self.font.render(self.score_text, 1, (255, 255, 255))
        self.credit_rect = Rect(self.x_credit, 288, self.credit_text_width, self.credit_text_height)
        self.over_rect = Rect(self.x_over, 190, self.over_text_width, self.over_text_height)
        self.next_rect = Rect(self.x_next, 190, self.next_text_width, self.next_text_height)
        self.credit_text = self.credit_font.render(self.credit_text_i, 1, (255, 255, 255))
        self.over_text = self.credit_font.render(self.over_text_i, 1, (255, 255, 255))
        self.next_text = self.credit_font.render(self.next_text_i, 1, (255, 255, 255))
        self.score_value_text = ''
        self.f1 = None
        self.font1 = txt.Font('Asset/ft.ttf', 100)
        self.score_rect = Rect(100, self.y_title+self.text_height, 100, 100)
        self.home_background_color = AmazeboyColor(240,230,140,255)

    def draw(self, state):

        if(state == 0):

            self.game_logo_rect = Rect(self.animated_count * 550, 0, 550, 550)

            self.game_logo_sprite = GameSprite(self.game_logo, self.game_logo_rect)

            self.game_logo_surface = self.game_logo_sprite.getImage()  # get game logo image

            self.scene.fill(self.home_background_color)
            self.scene.blit(self.game_logo_surface, self.draw_game_logo_pos) # draw a game logo
            self.scene.blit(self.play_button_surface, self.draw_play_button_pos)  # draw a button sprite
            self.scene.blit(self.about_button_surface, self.draw_about_button_pos)  # draw a button sprite
            self.scene.blit(self.score_button_surface, self.draw_score_button_pos)  # draw a button sprite
            self.scene.blit(self.manual_button_surface, self.draw_manual_button_pos)  # draw a button sprite
            self.scene.blit(self.exit_button_surface, self.draw_exit_button_pos)  # draw a button sprite
            self.scene.blit(self.scene_button_surface, self.draw_scene_button_pos)  # draw a button sprite
            if(self.soundon == True):
                self.scene.blit(self.soundon_button_surface, self.draw_sound_button_pos)  # draw a button sprite
            else:
                self.scene.blit(self.soundoff_button_surface, self.draw_sound_button_pos)  # draw a button sprite

            self.animated_count += 1
            if(self.animated_count > 6):
                self.animated_count = 0

        elif(state == 2):

            self.scene.fill(self.home_background_color)
            self.scene.blit(self.over_text, self.over_rect)  # the over text

        elif (state == 3):

            self.scene.fill(self.home_background_color)
            self.scene.blit(self.next_text, self.next_rect)  # the next text

        elif(state == 4):
            self.scene.blit(self.win_surface, self.draw_pos)  # draw a win sprite

        elif (state == 5):
            self.scene.fill(self.home_background_color) # draw a background
            self.scene.blit(self.credit_text, self.credit_rect)  # the credit text
            #self.scene.blit(self.about_surface, self.draw_pos)  # draw a about sprite
            self.scene.blit(self.home_button_surface, self.draw_back_button_pos)  # draw a button sprite

        elif (state == 6):
            self.scene.blit(self.manual_surface, self.draw_pos)  # draw a manual sprite
            self.scene.blit(self.home_button_surface, self.draw_back_button_pos)  # draw a button sprite

        elif (state == 7):

            self.scene.fill(self.home_background_color)  # draw a background
            self.scene.blit(self.play_button_surface, self.draw_play_button_pos)  # draw a button sprite
            self.scene.blit(self.home_pause_button_surface, self.draw_home_button_pos)  # draw a button sprite

        elif (state == 8):

            self.scene.fill(self.home_background_color)  # draw a background
            self.scene.blit(self.title_score_text, self.title_rect) # the score title first
            list_level = self.level_manager.get_list()

            for i in range(len(list_level)):
                self.score_rect = Rect(95, self.y_title + self.text_height + self.count * 90, 100, 100)
                self.score_value_text = str(self.count+1) + ".) Level " + str(list_level[i])
                self.value_score_text = self.font1.render(self.score_value_text, 1, (255, 255, 255))
                self.scene.blit(self.value_score_text, self.score_rect)  # the top 5 levels of the game
                self.count += 1

            self.count = 0

            self.scene.blit(self.home_button_surface, self.draw_back_button_pos)  # draw a button sprite

        if(state == 2 or state == 3 or state == 4):
            self.scene.blit(self.button_surface, self.draw_button_pos)  # draw a button sprite

        pygame.display.flip()

This is what you will see after that edit.

Have you downloaded the previous pygame project already? If not here is the download link.

In the next chapter we will continue to touch up more features.

The screenshot mechanism

I have just completed the screenshot mechanism for this latest pygame project. Basically, we will need to edit a few files in order to implement that mechanism.

The first file we need to edit is the scene class which will show all the screenshots that player has taken when he presses on the s key during the game stage!

from BgSprite import BgSprite
from GameSprite import GameSprite
from pygame.locals import *
from pygame import math as mt
import pygame

class Scene(object):

    def __init__(self, scene):

        self.scene = scene
        self.screen_folder = 'Screen/'
        self.next_button = 'Asset/back.png'
        self.previous_button = 'Asset/back.png'
        self.home_button = 'Asset/back.png'

        self.bg_rect = Rect(0, 0, 640, 640)
        self.next_button_rect = Rect(0, 0,  40, 30)
        self.previous_button_rect = Rect(0, 0, 40, 30)
        self.home_button_rect = Rect(0, 0, 40, 30)
        self.count = 0
        self.next = 1
        self.open_file()
        self.setup()

        self.previous_button_sprite = GameSprite(self.previous_button, self.previous_button_rect)
        self.next_button_sprite = GameSprite(self.next_button, self.next_button_rect)
        self.sprite_home_button = GameSprite(self.home_button, self.home_button_rect)


        self.previous_button_surface = self.previous_button_sprite.getImage() # get the button sprite surface
        self.next_button_surface = self.next_button_sprite.getImage()  # get the button sprite surface
        self.home_button_surface = self.sprite_home_button.getImage()  # get the button sprite surface

        self.draw_pos = mt.Vector2(0, 0)
        self.draw_next_button_pos = mt.Vector2(597, 330)
        self.draw_previous_button_pos = mt.Vector2(3, 344)
        self.draw_home_button_pos = mt.Vector2(10, 590)

    def open_file(self):

        try:
            f = open("Screen/count.txt", "r")

            try:
                if f.mode == 'r':
                    self.f1 = f.readlines()
                    for x in self.f1:
                        self.count = int(x)
            finally:
                f.close()


        except IOError:
            print('Error')

    def setup(self):

        if(self.count &gt; 0):
            self.general_image = 'Screen/' + str(self.next) + 'game.png'
        else:
            self.general_image = 'Asset/general.png'

        self.screen_sprite = BgSprite(self.general_image, self.bg_rect)
        self.screen_surface = self.screen_sprite.getImage()  # get the screen sprite surface


    def take_screen(self): # take screenshot
        self.count += 1
        self.file_path = 'Screen/' + str(self.count) + 'game.png'
        pygame.image.save(self.scene, self.file_path)
        self.save_file()

    def save_file(self):
        try:

            f = open("Screen/count.txt", "w+")
            try:
                f.write(str(self.count))
            finally:
                f.close()
        except IOError:
            print('cannot save a file')

    def set_next_image(self):

        self.next += 1
        if(self.next &gt; self.count):
            self.next = self.count

        self.setup()

    def set_previous_image(self):

        self.next -= 1

        if(self.next &lt;= 0):
            self.next = 1

        self.setup()

    def draw(self):

        self.scene.blit(self.screen_surface, self.draw_pos)  # draw a game scene sprite
        self.scene.blit(self.previous_button_surface, self.draw_previous_button_pos)  # draw a previous button sprite
        self.scene.blit(pygame.transform.flip(self.next_button_surface, True, False), self.draw_next_button_pos) # draw a next button sprite
        self.scene.blit(self.home_button_surface, self.draw_home_button_pos)  # draw a button sprite

        pygame.display.flip()

The next file we need to edit is the game manager class where it will ask the scene class to display the screenshot when the game state has been set to the scene state or to set the game state to the scene state if the user has pressed on the scene button on the main menu page. Besides that, it will also ask the scene class to take a screenshot and then saves that screenshot file when the user has pressed on the s key during the game stage.

from EnemyManager import EnemyManager
from Overlap import Overlap
from ExplosionManager import ExplosionManager
from Score import Score
from StartScene import StartScene
from pygame.locals import *
from LevelManager import LevelManager
import pygame
import webbrowser
from Scene import Scene
from BackGroundSprite import BackGroundSprite
from BoySprite import BoySprite
from ManaManager import ManaManager

class GameManager(object):

    def __init__(self, scene):

        self.scene = scene
        self.load_music()
        self.play_music()
        self.overlap_manager = Overlap()
        self.level_manager = LevelManager(self)
        self.level_manager.set_level()
        self.setup(self.level_manager.get_level())
        self.start_scene = StartScene(scene, self.level_manager)
        self.pause = False # flag to pause the game
        self.game_scene = Scene(self.scene)

        #game state
        self.LOAD = 0
        self.GAME = 1
        self.OVER = 2
        self.NEXT = 3
        self.WIN = 4
        self.ABOUT = 5
        self.MANUAL = 6
        self.PAUSE = 7
        self.SCORE = 8
        self.SCENE = 9

        self.state = self.LOAD

    def setup(self, game_level):

        self.game_level = game_level
        self.score_manager = Score(self.scene, self.level_manager)
        self.background = BackGroundSprite(game_level, self.scene)
        self.enemy_manager = EnemyManager(self.scene, game_level)
        self.mana_manager = ManaManager(self.scene, game_level)
        self.boy_sprite = BoySprite(self.scene, game_level, self.enemy_manager, self.mana_manager, self.level_manager)
        self.explosion_manager = ExplosionManager(self.scene)

    def loop(self):

        if(self.state == self.LOAD):
            self.start_scene.draw(self.state)
        elif(self.state == self.PAUSE or self.state == self.OVER or self.state == self.NEXT or self.state == self.WIN or self.state == self.ABOUT or self.state == self.MANUAL or self.state == self.SCORE):
            self.start_scene.draw(self.state)
        elif(self.state == self.SCENE):
            self.game_scene.draw()
        elif(self.state == self.GAME):

            self.update()
            self.draw()

    def isAreaClick(self, x, y):
        if (self.state == self.LOAD or self.state == self.OVER or self.state == self.NEXT or self.state == self.WIN or self.state == self.ABOUT or self.state == self.SCORE or self.state == self.SCENE or self.state == self.MANUAL or self.state == self.PAUSE):
            self.rect = Rect(177, 274, 306, 112) # the position of the play button on the scene
            self.rect_play = Rect(229, 200, 200, 53)  # the position of the play button on the home scene
            self.rect_about = Rect(229, 263, 200, 53)  # the position of the about button on the home scene
            #self.rect_exit = Rect(229, 456, 200, 53)  # the position of the exit button on the home scene
            self.rect_pause_home = Rect(229, 263, 200, 53)  # the position of the home button on pause scene
            self.rect_score = Rect(229, 328, 200, 53)  # the position of the score button on the home scene
            self.rect_manual = Rect(229, 393, 200, 53)  # the position of the manual button on the home scene
            self.rect_scene = Rect(229, 519, 200, 53)  # the position of the manual button on the home scene
            self.rect_back = Rect(10, 590, 40, 30)  # the position of the back button on the home scene
            self.rect_sound = Rect(10, 600, 30, 30) # the position of the sound button on the home scene
            self.rect_scene_next = Rect(597, 330, 40, 30)  # the position of the next scene button on scene
            self.rect_scene_previous = Rect(3, 344, 40, 30)  # the position of the previous scene button on scene

            if(self.rect.collidepoint(x, y) and (self.state == self.OVER or self.state == self.NEXT or self.state == self.WIN)):
                self.state = self.GAME
            elif(self.rect_play.collidepoint(x,y) and self.state == self.LOAD):
                self.state = self.GAME
            elif (self.rect_play.collidepoint(x, y) and self.state == self.PAUSE):
                self.state = self.GAME
            elif (self.rect_about.collidepoint(x, y) and self.state == self.LOAD):
                self.state = self.ABOUT
            elif (self.rect_score.collidepoint(x, y) and self.state == self.LOAD):
                self.state = self.SCORE
            elif (self.rect_scene.collidepoint(x, y) and self.state == self.LOAD):
                self.state = self.SCENE
            elif (self.rect_back.collidepoint(x, y) and self.state == self.SCENE):
                self.state = self.LOAD
            elif (self.rect_scene_next.collidepoint(x, y) and self.state == self.SCENE):
                self.game_scene.set_next_image()
            elif (self.rect_scene_previous.collidepoint(x, y) and self.state == self.SCENE):
                self.game_scene.set_previous_image()
            elif (self.rect_pause_home.collidepoint(x, y) and self.state == self.PAUSE):

                self.state = self.LOAD
                self.setup(self.level_manager.get_level())
                self.save_level()

            elif (self.rect_manual.collidepoint(x, y) and self.state == self.LOAD):
                webbrowser.open_new('http://gamingdirectional.com/blog/2018/12/25/air-strike//')
            elif (self.rect_back.collidepoint(x, y) and (self.state == self.ABOUT or self.state == self.MANUAL or self.state == self.SCORE)):
                self.state = self.LOAD
            elif (self.rect_sound.collidepoint(x, y) and self.state == self.LOAD):

                if(self.start_scene.soundon == True):
                    self.start_scene.soundon = False
                    pygame.mixer_music.pause()
                else:
                    self.start_scene.soundon = True
                    pygame.mixer_music.unpause()

    def save_level(self):
        self.level_manager.save_level()

    def set_pause(self, pause):

        self.pause = pause
        if(self.pause == True):

            self.state = self.PAUSE

    def load_music(self):
        pygame.mixer_music.load('Music/winternight.ogg')

    def play_music(self):
        pygame.mixer_music.play(-1) #play the music infinite time

    def set_player_x(self, _x):
        if (self.state == self.GAME):
            self.boy_sprite.setX(_x)

    def save_scene(self):
        self.game_scene.take_screen()

    def set_player_y(self, _y):
        if (self.state == self.GAME):
            self.boy_sprite.setY(_y)

    def update(self):
        self.enemy_manager.update()
        self.mana_manager.update()
        self.boy_sprite.update()

    def draw(self):
        if(self.state == self.GAME):
            self.background.draw()
            #self.score_manager.draw()
            self.boy_sprite.draw()
            self.enemy_manager.draw()
            self.mana_manager.draw()
            pygame.display.flip()

The final file which we need to edit is the main file which we will add in the s key event which will make the game manager class to ask the scene class to save the game scene.

import pygame
from pygame.locals import *
from GameManager import GameManager

pygame.init()

size = width, height = 640, 640
pygame.display.set_caption("Amaze Boy")  # set the title of the window
screen = pygame.display.set_mode(size)
game_manager = GameManager(screen)
rect_exit = Rect(229, 456, 200, 53)  # the position of the exit button on the home scene
running = True
pygame.key.set_repeat(100, 40)

while running:

    for event in pygame.event.get():
        # when the user clicks on the 'x'
        if event.type == pygame.QUIT:
            game_manager.save_level()
            running = False

        # detect key press event
        if event.type == KEYDOWN:

            if (game_manager.state == 1):

                if event.key == K_LEFT:
                    game_manager.set_player_x(-2)
                elif event.key == K_RIGHT:
                    game_manager.set_player_x(2)
                elif event.key == K_UP:
                    game_manager.set_player_y(-2)
                elif event.key == K_DOWN:
                    game_manager.set_player_y(2)

        elif event.type == KEYUP:

            if (game_manager.state == 1):

                if event.key == K_LEFT:
                    game_manager.set_player_x(0)
                elif event.key == K_RIGHT:
                    game_manager.set_player_x(0)
                elif event.key == K_UP:
                    game_manager.set_player_y(0)
                elif event.key == K_DOWN:
                    game_manager.set_player_y(0)
                elif event.key == K_p:
                    game_manager.set_pause(True)  # set the pause state to true
                elif event.key == K_s: # take the game screenshot
                    game_manager.save_scene()

        elif event.type == pygame.MOUSEBUTTONDOWN:
            x, y = event.pos
            if (rect_exit.collidepoint(x, y) and game_manager.state == game_manager.LOAD):
                game_manager.save_level()
                running = False
            # 1 is the left mouse button
            elif event.button == 1:
                game_manager.isAreaClick(x, y)

    game_manager.loop()

If you run the above program again and when you press on the s key on your keyboard during the game stage then this program will take a screenshot and saves it for later use!

Like, share or follow me on Twitter will give me strength to continue developing more pygame projects in the future.

The winning scene of the game

Hello and welcome back, in this article we will create the winning scene for this pygame project. Basically, we have already created those winning scene mechanisms in the last project where the game’s winning scene will pop up when the player has concurred all the levels, the player can then press on the play button to restart the game again if he wants to. Below are the three files that are involved in this process.

from BgSprite import BgSprite
from GameSprite import GameSprite
from pygame.locals import *
from pygame import math as mt
import pygame
import pygame.font as txt
from AmazeboyColor import AmazeboyColor

class StartScene(object):

    def __init__(self, scene, lm):

        self.level_manager = lm

        self.scene = scene
        self.play_button = 'Asset/play.png'
        self.about_button  = 'Asset/about.png'
        self.exit_button = 'Asset/exit.png'
        self.scene_button = 'Asset/scene.png'
        self.score_button = 'Asset/score.png'
        self.home_button = 'Asset/back.png'
        self.button_image = 'Asset/button_play.png'
        self.manual_button = 'Asset/manual.png'
        self.bg_image = 'Asset/start.png'
        self.win_image = 'Asset/winn.png'
        self.general_image = 'Asset/general.png'

        self.soundon = 'Asset/sound.png'
        self.soundoff = 'Asset/soundoff.png'
        self.home_button_image = 'Asset/home.png'
        self.game_logo = 'Asset/menu.png'
        self.bg_rect = Rect(0, 0, 640, 640)
        self.button_rect = Rect(0, 0,  306, 112)
        self.home_button_rect = Rect(0, 0, 200, 53)
        self.back_button_rect = Rect(0, 0, 40, 30)
        self.sound_button_rect = Rect(0, 0, 30, 30)

        self.animated_count = 0
        #self.game_logo_rect = Rect(self.animated_count*550, 0, 550, 550)

        self.sprite = BgSprite(self.general_image, self.bg_rect)


        self.sprite_win = BgSprite(self.win_image, self.bg_rect)

        self.sprite_pause = BgSprite(self.general_image, self.bg_rect)

        self.soundon_button = GameSprite(self.soundon, self.sound_button_rect)
        self.soundoff_button = GameSprite(self.soundoff, self.sound_button_rect)

        self.soundoff_button_surface = self.soundoff_button.getImage()  # get the button sprite surface
        self.soundon_button_surface = self.soundon_button.getImage()  # get the button sprite surface
        #self.game_logo_sprite = GameSprite(self.game_logo, self.game_logo_rect)
        self.sprite_button = GameSprite(self.button_image, self.button_rect)
        self.sprite_home_pause_button = GameSprite(self.home_button_image, self.home_button_rect)
        self.sprite_scene_button = GameSprite(self.scene_button, self.home_button_rect)
        self.sprite_manual_button = GameSprite(self.manual_button, self.home_button_rect)
        self.sprite_exit_button = GameSprite(self.exit_button, self.home_button_rect)
        self.sprite_play_button = GameSprite(self.play_button, self.home_button_rect)
        self.sprite_about_button = GameSprite(self.about_button, self.home_button_rect)
        self.sprite_score_button = GameSprite(self.score_button, self.home_button_rect)
        self.sprite_home_button = GameSprite(self.home_button, self.back_button_rect)

        self.win_surface = self.sprite_win.getImage()  # get the win sprite surface
        self.pause_surface = self.sprite_pause.getImage()  # get the pause sprite surface
        self.surface = self.sprite.getImage()  # get the start scene sprite surface
        self.button_surface = self.sprite_button.getImage() # get the button sprite surface
        self.home_pause_button_surface = self.sprite_home_pause_button.getImage() # get the button sprite surface
        self.play_button_surface = self.sprite_play_button.getImage()  # get the button sprite surface
        self.about_button_surface = self.sprite_about_button.getImage()  # get the button sprite surface
        self.score_button_surface = self.sprite_score_button.getImage()  # get the button sprite surface
        self.manual_button_surface = self.sprite_manual_button.getImage()  # get the button sprite surface
        self.scene_button_surface = self.sprite_scene_button.getImage()  # get the button sprite surface
        self.home_button_surface = self.sprite_home_button.getImage()  # get the button sprite surface
        self.exit_button_surface = self.sprite_exit_button.getImage()  # get the button sprite surface
        #self.game_logo_surface = self.game_logo_sprite.getImage() # get game logo image
        self.draw_pos = mt.Vector2(0, 0)
        self.draw_button_pos = mt.Vector2(177, 274)
        self.draw_game_logo_pos = mt.Vector2(170, 103)
        self.draw_play_button_pos = mt.Vector2(229, 200)
        self.draw_about_button_pos = mt.Vector2(229, 263)
        self.draw_home_button_pos = mt.Vector2(229, 263)
        self.draw_score_button_pos = mt.Vector2(229, 328)
        self.draw_manual_button_pos = mt.Vector2(229, 393)
        self.draw_exit_button_pos = mt.Vector2(229, 456)
        self.draw_scene_button_pos = mt.Vector2(229, 519)
        self.draw_back_button_pos = mt.Vector2(10, 620)

        self.draw_sound_button_pos = mt.Vector2(10, 600)

        self.soundon = True
        self.count = 0

        self.font = txt.Font('Asset/ft.ttf', 90)
        self.credit_font = txt.Font('Asset/ft.ttf', 50)
        self.score_text = "Top Achievements"
        self.credit_text_i = "Create by : IslandTropicalMan"
        self.over_text_i = "Game Over"
        self.next_text_i = "Next Level"
        self.text_width, self.text_height = self.font.size(self.score_text)
        self.credit_text_width, self.credit_text_height = self.credit_font.size(self.credit_text_i)
        self.over_text_width, self.over_text_height = self.credit_font.size(self.over_text_i)
        self.next_text_width, self.next_text_height = self.credit_font.size(self.next_text_i)
        self.x_title = 330 - self.text_width/2
        self.x_credit = 330 - self.credit_text_width/2
        self.x_over = 330 - self.over_text_width / 2
        self.x_next = 330 - self.next_text_width/2
        self.y_title = 60
        self.title_rect = Rect(self.x_title, self.y_title, self.text_width, self.text_height)
        self.title_score_text = self.font.render(self.score_text, 1, (255, 255, 255))
        self.credit_rect = Rect(self.x_credit, 330, self.credit_text_width, self.credit_text_height)
        self.over_rect = Rect(self.x_over, 190, self.over_text_width, self.over_text_height)
        self.next_rect = Rect(self.x_next, 190, self.next_text_width, self.next_text_height)
        self.credit_text = self.credit_font.render(self.credit_text_i, 1, (255, 255, 255))
        self.over_text = self.credit_font.render(self.over_text_i, 1, (255, 255, 255))
        self.next_text = self.credit_font.render(self.next_text_i, 1, (255, 255, 255))
        self.score_value_text = ''
        self.f1 = None
        self.font1 = txt.Font('Asset/ft.ttf', 100)
        self.score_rect = Rect(100, self.y_title+self.text_height, 100, 100)
        self.home_background_color = AmazeboyColor(240,230,140,255)

    def draw(self, state):

        if(state == 0):

            self.game_logo_rect = Rect(self.animated_count * 550, 0, 550, 550)

            self.game_logo_sprite = GameSprite(self.game_logo, self.game_logo_rect)

            self.game_logo_surface = self.game_logo_sprite.getImage()  # get game logo image

            self.scene.fill(self.home_background_color)
            self.scene.blit(self.game_logo_surface, self.draw_game_logo_pos) # draw a game logo
            self.scene.blit(self.play_button_surface, self.draw_play_button_pos)  # draw a button sprite
            self.scene.blit(self.about_button_surface, self.draw_about_button_pos)  # draw a button sprite
            self.scene.blit(self.score_button_surface, self.draw_score_button_pos)  # draw a button sprite
            self.scene.blit(self.manual_button_surface, self.draw_manual_button_pos)  # draw a button sprite
            self.scene.blit(self.exit_button_surface, self.draw_exit_button_pos)  # draw a button sprite
            self.scene.blit(self.scene_button_surface, self.draw_scene_button_pos)  # draw a button sprite
            if(self.soundon == True):
                self.scene.blit(self.soundon_button_surface, self.draw_sound_button_pos)  # draw a button sprite
            else:
                self.scene.blit(self.soundoff_button_surface, self.draw_sound_button_pos)  # draw a button sprite

            self.animated_count += 1
            if(self.animated_count > 6):
                self.animated_count = 0

        elif(state == 2):

            self.scene.fill(self.home_background_color)
            self.scene.blit(self.over_text, self.over_rect)  # the over text

        elif (state == 3):

            self.scene.fill(self.home_background_color)
            self.scene.blit(self.next_text, self.next_rect)  # the next text

        elif(state == 4):
            self.scene.blit(self.win_surface, self.draw_pos)  # draw a win sprite

        elif (state == 5):
            self.scene.fill(self.home_background_color) # draw a background
            self.scene.blit(self.credit_text, self.credit_rect)  # the credit text
            #self.scene.blit(self.about_surface, self.draw_pos)  # draw a about sprite
            self.scene.blit(self.home_button_surface, self.draw_back_button_pos)  # draw a button sprite

        elif (state == 6):
            self.scene.blit(self.manual_surface, self.draw_pos)  # draw a manual sprite
            self.scene.blit(self.home_button_surface, self.draw_back_button_pos)  # draw a button sprite

        elif (state == 7):
            #self.scene.blit(self.pause_surface, self.draw_pos)  # draw a pause sprite
            self.scene.fill(self.home_background_color)  # draw a background
            self.scene.blit(self.play_button_surface, self.draw_play_button_pos)  # draw a button sprite
            self.scene.blit(self.home_pause_button_surface, self.draw_home_button_pos)  # draw a button sprite

        elif (state == 8):

            self.scene.fill(self.home_background_color)  # draw a background
            self.scene.blit(self.title_score_text, self.title_rect) # the score title first
            list_level = self.level_manager.get_list()

            for i in range(len(list_level)):
                self.score_rect = Rect(95, self.y_title + self.text_height + self.count * 100, 100, 100)
                self.score_value_text = str(self.count+1) + ".) Level " + str(list_level[i])
                self.value_score_text = self.font1.render(self.score_value_text, 1, (255, 255, 255))
                self.scene.blit(self.value_score_text, self.score_rect)  # the top 5 levels of the game
                self.count += 1

            self.count = 0

            self.scene.blit(self.home_button_surface, self.draw_back_button_pos)  # draw a button sprite

        if(state == 2 or state == 3 or state == 4):
            self.scene.blit(self.button_surface, self.draw_button_pos)  # draw a button sprite

        pygame.display.flip()
import pickle

class LevelManager(object):

    def __init__(self, gm):

        self.game_manager = gm
        self.delete_line = False
        self.MAX_LEVEL = 2
        self.level = 1
        self.level_list = []

    def set_level(self):

        try:

            f = open("level.pickle", "rb")
            self.level_list = pickle.load(f)
            self.level = self.level_list[len(self.level_list) - 1]
            if (len(self.level_list) > 5):
                self.level_list.pop(0)

        except EOFError:
            self.level = 1
            self.level_list.append(self.level)

    def save_level(self):
        try:
            self.level_list.append(self.level)
            if(len(self.level_list) > 5):
                self.level_list.pop(0)
            f = open("level.pickle", "wb")
            pickle.dump(self.level_list, f)
            f.close()
        except IOError:
            print('cannot open a file')

    def increase_level(self):

        self.level += 1
        if(self.level >  self.MAX_LEVEL):
            self.game_manager.state = self.game_manager.WIN
            self.level = 1
            self.game_manager.setup(self.level)
        else:
            #self.game_manager.state = self.game_manager.NEXT
            self.game_manager.setup(self.level)

    def get_level(self):

        return self.level

    def reset_level(self):

        self.game_manager.setup(self.level)

    def get_list(self):

        return self.level_list
from EnemyManager import EnemyManager
from Overlap import Overlap
from ExplosionManager import ExplosionManager
from Score import Score
from StartScene import StartScene
from pygame.locals import *
from LevelManager import LevelManager
import pygame
import webbrowser
from Scene import Scene
from BackGroundSprite import BackGroundSprite
from BoySprite import BoySprite
from ManaManager import ManaManager

class GameManager(object):

    def __init__(self, scene):

        self.scene = scene
        self.load_music()
        self.play_music()
        self.overlap_manager = Overlap()
        self.level_manager = LevelManager(self)
        self.level_manager.set_level()
        self.setup(self.level_manager.get_level())
        self.start_scene = StartScene(scene, self.level_manager)
        self.pause = False # flag to pause the game
        self.game_scene = Scene(self.scene)

        #game state
        self.LOAD = 0
        self.GAME = 1
        self.OVER = 2
        self.NEXT = 3
        self.WIN = 4
        self.ABOUT = 5
        self.MANUAL = 6
        self.PAUSE = 7
        self.SCORE = 8
        self.SCENE = 9

        self.state = self.LOAD

    def setup(self, game_level):

        self.game_level = game_level
        self.score_manager = Score(self.scene, self.level_manager)
        self.background = BackGroundSprite(game_level, self.scene)
        self.enemy_manager = EnemyManager(self.scene, game_level)
        self.mana_manager = ManaManager(self.scene, game_level)
        self.boy_sprite = BoySprite(self.scene, game_level, self.enemy_manager, self.mana_manager, self.level_manager)
        self.explosion_manager = ExplosionManager(self.scene)

    def loop(self):

        if(self.state == self.LOAD):
            self.start_scene.draw(self.state)
        elif(self.state == self.OVER or self.state == self.NEXT or self.state == self.WIN or self.state == self.ABOUT or self.state == self.MANUAL or self.state == self.SCORE):
            self.start_scene.draw(self.state)
        elif(self.state == self.SCENE):
            self.game_scene.draw()
        elif(self.state == self.GAME):

            self.update()
            self.draw()

        elif(self.state == self.PAUSE):

            self.start_scene.draw(self.state)

    def isAreaClick(self, x, y):
        if (self.state == self.LOAD or self.state == self.OVER or self.state == self.NEXT or self.state == self.WIN or self.state == self.ABOUT or self.state == self.SCORE or self.state == self.SCENE or self.state == self.MANUAL or self.state == self.PAUSE):
            self.rect = Rect(177, 274, 306, 112) # the position of the play button on the scene
            self.rect_play = Rect(229, 200, 200, 53)  # the position of the play button on the home scene
            self.rect_about = Rect(229, 263, 200, 53)  # the position of the about button on the home scene
            #self.rect_exit = Rect(229, 456, 200, 53)  # the position of the exit button on the home scene
            self.rect_pause_home = Rect(229, 263, 200, 53)  # the position of the home button on pause scene
            self.rect_score = Rect(229, 328, 200, 53)  # the position of the score button on the home scene
            self.rect_manual = Rect(229, 393, 200, 53)  # the position of the manual button on the home scene
            self.rect_scene = Rect(229, 519, 200, 53)  # the position of the manual button on the home scene
            self.rect_back = Rect(10, 620, 40, 30)  # the position of the back button on the home scene
            self.rect_sound = Rect(10, 600, 30, 30) # the position of the sound button on the home scene
            self.rect_scene_next = Rect(610, 330, 30, 30)  # the position of the next scene button on scene
            self.rect_scene_previous = Rect(50, 330, 30, 30)  # the position of the previous scene button on scene

            if(self.rect.collidepoint(x, y) and (self.state == self.OVER or self.state == self.NEXT or self.state == self.WIN)):
                self.state = self.GAME
            elif(self.rect_play.collidepoint(x,y) and self.state == self.LOAD):
                self.state = self.GAME
            elif (self.rect_play.collidepoint(x, y) and self.state == self.PAUSE):
                self.state = self.GAME
            elif (self.rect_about.collidepoint(x, y) and self.state == self.LOAD):
                self.state = self.ABOUT
            elif (self.rect_score.collidepoint(x, y) and self.state == self.LOAD):
                self.state = self.SCORE
            elif (self.rect_scene.collidepoint(x, y) and self.state == self.LOAD):
                self.state = self.SCENE
            elif (self.rect_back.collidepoint(x, y) and self.state == self.SCENE):
                self.state = self.LOAD
            elif (self.rect_scene_next.collidepoint(x, y) and self.state == self.SCENE):
                self.game_scene.set_next_image()
            elif (self.rect_scene_previous.collidepoint(x, y) and self.state == self.SCENE):
                self.game_scene.set_previous_image()
            elif (self.rect_pause_home.collidepoint(x, y) and self.state == self.PAUSE):

                self.state = self.LOAD
                self.setup(self.level_manager.get_level())
                self.save_level()

            elif (self.rect_manual.collidepoint(x, y) and self.state == self.LOAD):
                webbrowser.open_new('http://gamingdirectional.com/blog/2018/12/25/air-strike//')
            elif (self.rect_back.collidepoint(x, y) and (self.state == self.ABOUT or self.state == self.MANUAL or self.state == self.SCORE)):
                self.state = self.LOAD
            elif (self.rect_sound.collidepoint(x, y) and self.state == self.LOAD):

                if(self.start_scene.soundon == True):
                    self.start_scene.soundon = False
                    pygame.mixer_music.pause()
                else:
                    self.start_scene.soundon = True
                    pygame.mixer_music.unpause()

    def save_level(self):
        self.level_manager.save_level()

    def set_pause(self, pause):

        self.pause = pause
        if(self.pause == True):

            self.state = self.PAUSE

    def load_music(self):
        pygame.mixer_music.load('Music/winternight.ogg')

    def play_music(self):
        pygame.mixer_music.play(-1) #play the music infinite time

    def set_player_x(self, _x):
        if (self.state == self.GAME):
            self.boy_sprite.setX(_x)

    def save_scene(self):
        self.game_scene.take_screen()

    def set_player_y(self, _y):
        if (self.state == self.GAME):
            self.boy_sprite.setY(_y)

    def update(self):
        self.enemy_manager.update()
        self.mana_manager.update()
        self.boy_sprite.update()

    def draw(self):
        if(self.state == self.GAME):
            self.background.draw()
            #self.score_manager.draw()
            self.boy_sprite.draw()
            self.enemy_manager.draw()
            self.mana_manager.draw()
            pygame.display.flip()

If you run the program again then you will see this outcome.

Basically, this pygame project has completed, what we will do in the next few chapters is to tidy up this project or perhaps to include a few new features into it.

Edit the level 2 game map

It has been a day since the last post, I am really busy recently working on the offline business so I really need to divide the time equally for both the online and the offline business. In this chapter, we will finish up the previous unfinished business which is to come out with a new game map for level 2. We need to edit those level 2 data for the player, the enemy, the background and the mana object as follows.

class BoyObject(object):

    def __init__(self):

        self.list_1 = [

            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [1, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
        ]

        self.ladder_boundary_1 = [[9 * 64, 8 * 64],
                                  [9 * 64, 7 * 64],
                                  [5 * 64, 6 * 64],
                                  [5 * 64, 5 * 64],
                                  [2 * 64, 3 * 64],
                                  [2 * 64, 4 * 64],
                                  [0 * 64, 1 * 64],
                                  [0 * 64, 2 * 64],
                                  ] # the boundary of the ladder

        self.boundary_bottom_1 = [[9 * 64, 9 * 64],
                                  [5 * 64, 7 * 64],
                                  [2 * 64, 5 * 64],
                                  [0 * 64, 3 * 64]]  # the bottom boundary of the ladder

        self.boundary_side_1 = [[4 * 64, 6 * 64],
                                [1 * 64, 4 * 64],
                                [6 * 64, 2 * 64], ]  # the side boundary of the player

        self.boundary_door_1 = [[9 * 64, 0]]

        self.initial_1 = [0, 8 * 64]

        self.list_2 = [

            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [1, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
        ]

        self.ladder_boundary_2 = [[9 * 64, 8 * 64],
                                  [9 * 64, 7 * 64],
                                  [2 * 64, 6 * 64],
                                  [2 * 64, 5 * 64],
                                  [2 * 64, 4 * 64],
                                  [2 * 64, 3 * 64],
                                  [8 * 64, 1 * 64],
                                  [8 * 64, 2 * 64],
                                  ]  # the boundary of the ladder

        self.boundary_bottom_2 = [[9 * 64, 9 * 64],
                                  [2 * 64, 7 * 64],
                                  [8 * 64, 3 * 64]]  # the bottom boundary of the ladder

        self.boundary_side_2 = [[1 * 64, 6 * 64],
                                [0 * 64, 2 * 64],]  # the side boundary of the player

        self.boundary_door_2 = [[0, 0]]

        self.initial_2 = [0, 8 * 64]

    def get_original_position(self, level):

        if (level == 1):
            return self.initial_1
        elif (level == 2):
            return self.initial_2

    def get_object_list(self, level):

        if(level == 1):
            return self.list_1
        elif (level == 2):
            return self.list_2

    def get_object_boundary(self, level):

        if (level == 1):
            return self.ladder_boundary_1
        elif (level == 2):
            return self.ladder_boundary_2

    def get_object_bottom_boundary(self, level):

        if (level == 1):
            return self.boundary_bottom_1
        elif (level == 2):
            return self.boundary_bottom_2

    def get_object_side_boundary(self, level):

        if (level == 1):
            return self.boundary_side_1
        elif (level == 2):
            return self.boundary_side_2

    def get_object_door_boundary(self, level):

        if(level == 1):
            return self.boundary_door_1
        elif (level == 2):
            return self.boundary_door_2
class EnemyObject(object):

    def __init__(self):

        self.list_1 = [

            [0, 1, 0, 0, 0, 1, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 1, 0, 0, 0, 1, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 1, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
        ]

        self.boundary_1 = [
            [[0, 0], [8 * 64, 0]],
            [[0, 0], [8 * 64, 0]],
            [[2 * 64, 4 * 64], [8 * 64, 4 * 64]],
            [[2 * 64, 4 * 64], [8 * 64, 4 * 64]],
            [[5 * 64, 6 * 64], [8 * 64, 6 * 64]]
        ]

        self.initial_1 = [[64, 0], [5 * 64, 0],[4 * 64, 4 * 64], [8 * 64, 4 * 64],[6 * 64, 6 * 64]]

        self.list_2 = [

            [0, 0, 0, 0, 0, 1, 0, 1, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 1, 0, 1, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 1, 0, 1, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 1, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
        ]

        self.boundary_2 = [
            [[0, 0], [9 * 64, 0]],
            [[0, 0], [9 * 64, 0]],
            [[0, 2 * 64], [9 * 64, 2 * 64]],
            [[0, 2 * 64], [9 * 64, 2 * 64]],
            [[2 * 64, 6 * 64], [9 * 64, 6 * 64]],
            [[2 * 64, 6 * 64], [9 * 64, 6 * 64]],
            [[0, 8 * 64], [9 * 64, 8 * 64]],
        ]

        self.initial_2 = [[64, 0], [5 * 64, 0], [3 * 64, 2 * 64], [5 * 64, 2 * 64], [3 * 64, 6 * 64], [5 * 64, 6 * 64],[4 * 64, 8 * 64] ]

    def get_original_position(self, level):

        if (level == 1):
            return self.initial_1
        elif (level == 2):
            return self.initial_2

    def get_object_list(self, level):

        if(level == 1):
            return self.list_1
        elif (level == 2):
            return self.list_2

    def get_object_boundary(self, level):

        if (level == 1):
            return self.boundary_1
        elif (level == 2):
            return self.boundary_2
class ManaObject(object):

    def __init__(self):

        self.list_1 = [

            [1, 1, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 1, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 1, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
        ]

        self.initial_1 = [[3 * 64, 8 * 64], [6 * 64, 6 * 64],[0 * 64, 0 * 64], [1 * 64, 0 * 64]]

        self.list_2 = [

            [0, 0, 0, 0, 0, 1, 1, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 1, 1, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 1, 1, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 1, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
        ]

        self.initial_2 = [[1 * 64, 8 * 64], [6 * 64, 6 * 64], [7 * 64, 6 * 64], [3 * 64, 2 * 64],[4 * 64, 2 * 64],[5 * 64, 0 * 64], [6 * 64, 0 * 64]]

    def get_original_position(self, level):

        if (level == 1):
            return self.initial_1
        elif (level == 2):
            return self.initial_2

    def get_object_list(self, level):

        if(level == 1):
            return self.list_1
        elif (level == 2):
            return self.list_2
class BgObject(object):

    def __init__(self):

        self.list_1 = [
            [3, 3, 3, 3, 3, 3, 3, 3, 3, 2],
            [4, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [4, 3, 3, 3, 3, 3, 3, 3, 3, 3],
            [0, 0, 4, 0, 0, 0, 3, 3, 3, 3],
            [3, 3, 4, 3, 3, 3, 3, 3, 3, 3],
            [0, 0, 0, 0, 1, 4, 1, 0, 0, 1],
            [3, 3, 3, 3, 3, 4, 3, 3, 3, 3],
            [3, 3, 3, 3, 3, 1, 1, 0, 0, 4],
            [3, 3, 3, 3, 3, 3, 3, 3, 3, 4],
            [0, 1, 0, 0, 1, 1, 0, 1, 1, 0]
        ]

        self.list_2 = [
            [2, 3, 3, 3, 3, 3, 3, 3, 3, 3],
            [1, 0, 0, 0, 0, 0, 0, 0, 4, 0],
            [3, 3, 3, 3, 3, 3, 3, 3, 4, 3],
            [3, 0, 4, 0, 0, 0, 0, 0, 0, 0],
            [3, 3, 4, 3, 3, 3, 3, 3, 3, 3],
            [3, 3, 4, 3, 3, 3, 3, 3, 3, 3],
            [3, 3, 4, 3, 3, 3, 3, 3, 3, 3],
            [3, 3, 0, 0, 0, 1, 1, 0, 0, 4],
            [3, 3, 3, 3, 3, 3, 3, 3, 3, 4],
            [0, 1, 0, 0, 1, 1, 0, 1, 1, 0]
        ]

    def get_object_list(self, level):

        if(level == 1):
            return self.list_1
        elif(level == 2):
            return self.list_2

Besides the above, we also need to make sure to change the number under the create enemy method of the enemy sprite class for level 2.

    def create_enemy(self, level):

        self.enemy_boundary_list = self.enemy_object.get_object_boundary(level)
        self.enemy_original_position = self.enemy_object.get_original_position(level)

        i = 0
        if(level == 1):
            while(i < 5):
                self.total_enemy_list.append(Enemy(self.enemy_boundary_list[i], self.enemy_original_position[i]))
                i += 1
        elif (level == 2):
            while (i < 7):
                self.total_enemy_list.append(Enemy(self.enemy_boundary_list[i], self.enemy_original_position[i]))
                i += 1

The same goes to the create mana method of the mana sprite class.

    def create_mana(self, level):

        self.mana_original_position = self.mana_object.get_original_position(level)

        i = 0
        if(level == 1):
            while(i < 4):
                self.total_mana_list.append(Mana(self.mana_original_position[i]))
                i += 1
        elif (level == 2):
            while (i < 7):
                self.total_mana_list.append(Mana(self.mana_original_position[i]))
                i += 1

If you run the above program again you will see this result.

Basically this project is almost completed, just a few touch up need to be done so stay tune for the next chapter.

Rotate the mana object

In this chapter, we will continue to develop the mana object. We will rotate the mana object on each update. If you still remember that we have created an update method under the mana class then in this chapter we will update the rotation angle position of that mana object accordingly on each update under this method. We will also create the get height and get width method so that mana object will return both the width and the height of that mana object that will be used by the mana sprite class to calculate the new position of the mana object on the game scene before drawing it. We also used the clock object from the pygame.time module to control the speed of rotation.

from pygame.locals import *
from GameSprite import GameSprite
import pygame

class Mana(object):

    def __init__(self, original_position_list):

        self.count = 0

        #original location for mana object

        self.x = original_position_list[0]
        self.y = original_position_list[1]

        self.alive = True

        # the width and height of mana
        self.w = 64
        self.h = 64

        self.clock = pygame.time.Clock()
        self.rotation = 0. # the rotation angle of the mana
        self.rotation_speed = 360.  # 360 degrees per second
        self.rotation_direction = 1.0

        self.mana_image_sprite_right = 'Asset/right.png'

        self.create_surface(self.mana_image_sprite_right)

    def create_surface(self, mana_image_sprite):

        self.mana_rect = Rect(7 * 64, 0, 64, 64)
        self.sprite = GameSprite(mana_image_sprite, self.mana_rect)
        self.sprite_surface = self.sprite.getImage()
        self.rotated_surface = self.sprite_surface # the mana rotate surface which will be returned by the mana object

    def update(self):

        self.rotated_surface = pygame.transform.rotate(self.sprite_surface, self.rotation ) # Return the rotated mana surface object
        self.w, self.h = self.rotated_surface.get_size()

        self.time_passed_seconds = (self.clock.tick())/ 2600.0

        self.rotation += self.rotation_direction * self.rotation_speed * self.time_passed_seconds

    def get_mana_surface(self):

        return self.rotated_surface

    def get_width(self):

        return self.w

    def get_height(self):

        return self.h

Finally, we will edit the mana sprite file accordingly to draw the rotating mana object on the game scene.

from pygame import math as mt
from Mana import Mana
from ManaObject import ManaObject

class ManaSprite(object):

    def __init__(self, level, scene):

        self.row = 10
        self.column = 10
        self.scene = scene # game scene instance
        self.space = 64 # image width and height

        self.level = level # current game level

        self.total_mana_list = []

        self.mana_object = ManaObject()

        self.create_mana(level)

    def create_mana(self, level):

        self.mana_original_position = self.mana_object.get_original_position(level)

        i = 0
        if(level == 1):
            while(i < 4):
                self.total_mana_list.append(Mana(self.mana_original_position[i]))
                i += 1

    def update(self):

        for mana in self.total_mana_list:
            mana.update()

    def draw(self):
        self.counter = 0
        for row in range(self.row):

            for column in range(self.column):

                if(self.mana_list[row][column] == 1):

                    self.mana = self.total_mana_list[self.counter]
                    if(self.mana.alive == True):
                        self.draw_pos = mt.Vector2(self.mana.x - self.mana.get_width()/7, self.mana.y - self.mana.get_height()/7)  # the position of the image on game scene
                        self.scene.blit(self.mana.get_mana_surface(), self.draw_pos)  # draw mana object
                    self.counter += 1

    def get_level(self, level):
        self.mana_list = self.mana_object.get_object_list(level)

    def get_mana_list(self):
        return self.total_mana_list

Here is the product of the above program.

Detect the next game level

Hello and welcome back to the current pygame project. In this article, we will create a new method to determine whether the boy has reached the door or not and if he did then the player will reach the next level. We will not create a new level yet so in this case, the game will restart again after the boy has reached the door. We will also temporary mute the player-enemy collision detection method because without the mana the boy will collide with the enemy and it will be a game over before the boy reaches the door, we will create the mana class in the next chapter. There are two files we need to edit in this chapter, first we will add in the door position list in the boy object class.

class BoyObject(object):

    def __init__(self):

        self.list_1 = [

            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [1, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            [0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
        ]

        self.ladder_boundary_1 = [[9 * 64, 8 * 64],
                                  [9 * 64, 7 * 64],
                                  [5 * 64, 6 * 64],
                                  [5 * 64, 5 * 64],
                                  [2 * 64, 3 * 64],
                                  [2 * 64, 4 * 64],
                                  [0 * 64, 1 * 64],
                                  [0 * 64, 2 * 64],
                                  ] # the boundary of the ladder

        self.boundary_bottom_1 = [[9 * 64, 9 * 64],
                                  [5 * 64, 7 * 64],
                                  [2 * 64, 5 * 64],
                                  [0 * 64, 3 * 64]]  # the bottom boundary of the ladder

        self.boundary_side_1 = [[4 * 64, 6 * 64],
                                [1 * 64, 4 * 64],
                                [6 * 64, 2 * 64], ]  # the side boundary of the player

        self.boundary_door_1 = [[9 * 64, 0]]

        self.initial_1 = [0, 8 * 64]

    def get_original_position(self, level):

        if (level == 1):
            return self.initial_1

    def get_object_list(self, level):

        if(level == 1):
            return self.list_1

    def get_object_boundary(self, level):

        if (level == 1):
            return self.ladder_boundary_1

    def get_object_bottom_boundary(self, level):

        if (level == 1):
            return self.boundary_bottom_1

    def get_object_side_boundary(self, level):

        if (level == 1):
            return self.boundary_side_1

    def get_object_door_boundary(self, level):

        if(level == 1):
            return self.boundary_door_1

Next, we will create the check win method in the boy sprite class to determine whether the boy has reached the door or not, we will temporary mute the check collide method as mentioned above.

from BoyObject import BoyObject
from pygame import math as mt
from pygame.locals import *
from GameSprite import GameSprite

class BoySprite(object):

    def __init__(self, scene, level, enemy_manager):

        self.row = 10
        self.column = 10
        self.scene = scene # game scene instance
        self.space = 64 # image width and height
        self.level = level # current game level
        self.enemy_manager = enemy_manager # the reference of enemy manager
        self.WIDTH = 640
        self.prepare_boy(self.level)

    def prepare_boy(self, level):
        self.boy_object = BoyObject()
        self.boy_object_list = self.boy_object.get_object_list(level)
        self.boy_original_position = self.boy_object.get_original_position(level)
        self.x = self.boy_original_position[0]
        self.y = self.boy_original_position[1]
        self.speed = 2
        self.boy_image_sprite_right = 'Asset/bright.png'
        self.boy_image_sprite_left = 'Asset/bleft.png'
        self.boy_sprite = self.boy_image_sprite_right
        self.frame = 3
        self.up = False
        self.ladder = False
        self.left = False
        self.boy_rect = Rect(self.frame * 64, 0, 64, 64)
        self.sprite_boy = GameSprite(self.boy_sprite, self.boy_rect)
        self.boy_surface = self.sprite_boy.getImage()
        self.boy_ladder_list = self.boy_object.get_object_boundary(level)
        self.boy_bottom_boundary_list = self.boy_object.get_object_bottom_boundary(level)
        self.boy_side_boundary_list = self.boy_object.get_object_side_boundary(level)
        self.boy_door_boundary_list = self.boy_object.get_object_door_boundary(level)
        self.enemy_list = self.enemy_manager.get_enemy_list()
        self.initialize()

    # set the x and the y direction for the player object

    def setX(self, x):

        if(self.ladder == True):
            return
        self.x += x
        if (self.up == True and x < 0):
            self.frame = 1
            self.up = False
        elif(self.up == True and x > 0):
            self.frame = 0
            self.up = False
        if(x < 0):
            self.left = True
            self.frame += 1
            if (self.frame > 5):
                self.frame = 1
            self.boy_sprite = self.boy_image_sprite_left
        elif(x > 0):
            self.frame += 1
            self.left = False
            if (self.frame > 4):
                self.frame = 0
            self.boy_sprite = self.boy_image_sprite_right
        elif(x == 0):
            if(self.left == True):
                self.frame = 2
                self.boy_sprite = self.boy_image_sprite_left
            elif(self.left == False):
                self.frame = 3
                self.boy_sprite = self.boy_image_sprite_right
        self.boy_rect = Rect(self.frame * 64, 0, 64, 64)
        self.sprite_boy = GameSprite(self.boy_sprite, self.boy_rect)
        self.boy_surface = self.sprite_boy.getImage()

    def setY(self, y):

        self.boy_rect = Rect(self.x, self.y+y, 64, 64)
        if(self.isUpDown(self.boy_rect, y) == True):
            self.y += y
        if(y == 0):
            self.frame = 9
        elif(self.up == False):
            self.frame = 6
            self.up = True
        else:
            if(y < 0):
                self.frame -= 1
            elif(y > 0):
                self.frame += 1
            if(self.frame > 10):
                self.frame = 6
            elif(self.frame < 6):
                self.frame += 2
        self.boy_sprite = self.boy_image_sprite_right
        self.boy_rect = Rect(self.frame * 64, 0, 64, 64)
        self.sprite_boy = GameSprite(self.boy_sprite, self.boy_rect)
        self.boy_surface = self.sprite_boy.getImage()

    def checkboundary(self):

        if(self.x < 0):
            self.x = 0
        elif(self.x > self.WIDTH - self.space):
            self.x = self.WIDTH - self.space
        else:
            self.isLeftRight()

    def isUpDown(self, rect, y):

        for boundary in self.boy_ladder_list:
            boundary_rect = Rect(boundary[0], boundary[1], 64, 64)
            if ((boundary_rect.collidepoint(self.x, self.y+y) == True or boundary_rect.collidepoint(self.x, self.y+self.space+y) == True) and (self.x % self.space == 0)):
                for boundary_bottom in self.boy_bottom_boundary_list:
                    boundary_rect = Rect(boundary_bottom[0], boundary_bottom[1], 64, 64)
                    if (boundary_rect.colliderect(rect) == True):
                        self.ladder = False
                        return False
                self.ladder = True
                return True
        self.ladder = False
        return False

    def isLeftRight(self):

        for boundary in self.boy_side_boundary_list:
            boundary_rect = Rect(boundary[0], boundary[1], 64, 64)
            boy_rect = Rect(self.x, self.y, 64, 64)
            if (boundary_rect.colliderect(boy_rect) == True):
                if(self.left == True):
                    self.x += self.speed
                else:
                    self.x -= self.speed

    def update(self):
        self.checkboundary()
        #self.check_collide()
        self.check_win()
        self.move_boy()

    def check_win(self):
        for door in self.boy_door_boundary_list:
            if(door[0] == self.x and door[1] == self.y):
                self.prepare_boy(self.level)

    def check_collide(self):
        for enemy in self.enemy_list:
            enemy_rect = Rect(enemy.x, enemy.y, 64, 64)
            boy_rect = Rect(self.x, self.y, 64, 64)
            if (enemy_rect.colliderect(boy_rect) == True):
                self.prepare_boy(self.level)
                return

    def move_boy(self):
        self.draw_pos = mt.Vector2(self.x, self.y)  # the position of the image on game scene

    def initialize(self):
        for row in range(self.row):
            for column in range(self.column):

                if(self.boy_object_list[row][column] == 1):

                    self.draw_pos = mt.Vector2(self.x, self.y)  # the vector position of the image on game scene
                    self.scene.blit(self.boy_surface, self.draw_pos)  # draw enemy frame

    def draw(self):

        self.scene.blit(self.boy_surface, self.draw_pos)  # draw boy frame

With that, when the boy has finally reached the door position the game will restart again.

Like, share or subscribe the above tweet or follow me on twitter.

Adjust the boy sprite animation

Hello, and welcome back, we are almost done coding the player animation mechanism after we have finished the player boundary detection mechanism in the last article but before we can go to the next stage we need to tidy up the player animation mechanism first by introducing the standstill image of the boy when the boy is not moving and that image will either face left or right or up or down based on the direction of the boy at the time he stops moving. In order to achieve this we only need to edit two files.

The first file we need to edit is the main file where we will include the keyup event so we can set the x different or y different to zero when the boy who is moving in either x or y-direction suddenly stop moving.

import pygame
from pygame.locals import *
from GameManager import GameManager

pygame.init()

size = width, height = 640, 640
pygame.display.set_caption("Amaze Boy")  # set the title of the window
screen = pygame.display.set_mode(size)
game_manager = GameManager(screen)
rect_exit = Rect(229, 456, 200, 53)  # the position of the exit button on the home scene
running = True
pygame.key.set_repeat(100, 40)

while running:

    for event in pygame.event.get():
        # when the user clicks on the 'x'
        if event.type == pygame.QUIT:
            game_manager.save_level()
            running = False

        # detect key press event
        if event.type == KEYDOWN:

            if (game_manager.state == 1):

                if event.key == K_LEFT:
                    game_manager.set_player_x(-2)
                elif event.key == K_RIGHT:
                    game_manager.set_player_x(2)
                elif event.key == K_UP:
                    game_manager.set_player_y(-2)
                elif event.key == K_DOWN:
                    game_manager.set_player_y(2)

        elif event.type == KEYUP:

            if (game_manager.state == 1):

                if event.key == K_LEFT:
                    game_manager.set_player_x(0)
                elif event.key == K_RIGHT:
                    game_manager.set_player_x(0)
                elif event.key == K_UP:
                    game_manager.set_player_y(0)
                elif event.key == K_DOWN:
                    game_manager.set_player_y(0)

        elif event.type == pygame.MOUSEBUTTONDOWN:
            x, y = event.pos
            if (rect_exit.collidepoint(x, y) and game_manager.state == game_manager.LOAD):
                game_manager.save_level()
                running = False
            # 1 is the left mouse button
            elif event.button == 1:
                game_manager.isAreaClick(x, y)

    game_manager.loop()

The next file we need to edit is the boy sprite class file where we will set the frame of the image to that of a standstill image of the boy depends on whether the boy is moving side-way or up-down before stopping.

from BoyObject import BoyObject
from pygame import math as mt
from pygame.locals import *
from GameSprite import GameSprite

class BoySprite(object):

    def __init__(self, scene, level):

        self.row = 10
        self.column = 10
        self.scene = scene # game scene instance
        self.space = 64 # image width and height
        self.level = level # current game level
        self.frame = 3
        self.prepare_boy(self.level)
        self.WIDTH = 640

    def prepare_boy(self, level):
        self.boy_object = BoyObject()
        self.boy_object_list = self.boy_object.get_object_list(level)
        self.boy_original_position = self.boy_object.get_original_position(level)
        self.x = self.boy_original_position[0]
        self.y = self.boy_original_position[1]
        self.speed = 2
        self.boy_image_sprite_right = 'Asset/bright.png'
        self.boy_image_sprite_left = 'Asset/bleft.png'
        self.boy_sprite = self.boy_image_sprite_right
        self.left = False
        self.up = False
        self.ladder = False
        self.boy_rect = Rect(self.frame * 64, 0, 64, 64)
        self.sprite_boy = GameSprite(self.boy_sprite, self.boy_rect)
        self.boy_surface = self.sprite_boy.getImage()
        self.boy_ladder_list = self.boy_object.get_object_boundary(level)
        self.boy_bottom_boundary_list = self.boy_object.get_object_bottom_boundary(level)
        self.boy_side_boundary_list = self.boy_object.get_object_side_boundary(level)
        self.initialize()

    # set the x and y direction for the player object

    def setX(self, x):

        if(self.ladder == True):
            return
        self.x += x
        if (self.up == True and x < 0):
            self.frame = 1
            self.up = False
        elif(self.up == True and x > 0):
            self.frame = 0
            self.up = False
        if(x < 0):
            self.left = True
            self.frame += 1
            if (self.frame > 5):
                self.frame = 1
            self.boy_sprite = self.boy_image_sprite_left
        elif(x > 0):
            self.frame += 1
            self.left = False
            if (self.frame > 4):
                self.frame = 0
            self.boy_sprite = self.boy_image_sprite_right
        elif(x == 0):
            if(self.left == True):
                self.frame = 2
                self.boy_sprite = self.boy_image_sprite_left
            elif(self.left == False):
                self.frame = 3
                self.boy_sprite = self.boy_image_sprite_right
        self.boy_rect = Rect(self.frame * 64, 0, 64, 64)
        self.sprite_boy = GameSprite(self.boy_sprite, self.boy_rect)
        self.boy_surface = self.sprite_boy.getImage()

    def setY(self, y):

        self.boy_rect = Rect(self.x, self.y+y, 64, 64)
        if(self.isUpDown(self.boy_rect, y) == True):
            self.y += y
        if(y == 0):
            self.frame = 9
        elif(self.up == False):
            self.frame = 6
            self.up = True
        else:
            if(y < 0):
                self.frame -= 1
            elif(y > 0):
                self.frame += 1
            if(self.frame > 10):
                self.frame = 6
            elif(self.frame < 6):
                self.frame += 2
        self.boy_sprite = self.boy_image_sprite_right
        self.boy_rect = Rect(self.frame * 64, 0, 64, 64)
        self.sprite_boy = GameSprite(self.boy_sprite, self.boy_rect)
        self.boy_surface = self.sprite_boy.getImage()

    def checkboundary(self):

        if(self.x < 0):
            self.x = 0
        elif(self.x > self.WIDTH - self.space):
            self.x = self.WIDTH - self.space
        else:
            self.isLeftRight()


    def isUpDown(self, rect, y):

        for boundary in self.boy_ladder_list:
            boundary_rect = Rect(boundary[0], boundary[1], 64, 64)
            if ((boundary_rect.collidepoint(self.x, self.y+y) == True or boundary_rect.collidepoint(self.x, self.y+self.space+y) == True) and (self.x % self.space == 0)):
                for boundary_bottom in self.boy_bottom_boundary_list:
                    boundary_rect = Rect(boundary_bottom[0], boundary_bottom[1], 64, 64)
                    if (boundary_rect.colliderect(rect) == True):
                        self.ladder = False
                        return False
                self.ladder = True
                return True
        self.ladder = False
        return False

    def isLeftRight(self):

        for boundary in self.boy_side_boundary_list:
            boundary_rect = Rect(boundary[0], boundary[1], 64, 64)
            boy_rect = Rect(self.x, self.y, 64, 64)
            if (boundary_rect.colliderect(boy_rect) == True):
                if(self.left == True):
                    self.x += self.speed
                else:
                    self.x -= self.speed

    def update(self):
        self.checkboundary()
        self.move_boy()

    def move_boy(self):
        self.draw_pos = mt.Vector2(self.x, self.y)  # the position of the image on game scene

    def initialize(self):
        for row in range(self.row):
            for column in range(self.column):

                if(self.boy_object_list[row][column] == 1):

                    self.draw_pos = mt.Vector2(self.x, self.y)  # the vector position of the image on game scene
                    self.scene.blit(self.boy_surface, self.draw_pos)  # draw enemy frame

    def draw(self):

        self.scene.blit(self.boy_surface, self.draw_pos)  # draw boy frame

With that, we will see a standstill image of the boy after the boy has stopped moving.

In the next chapter, we will explore the boy and the enemy overlapping detection mechanism. If you want to help this site please consider to donate through the below button, all your support will go to upgrading this site which will then provide you with a lot of new free code in the future, thank you in advance.