Pygame develops Flappy Bird games

Posted by liro on Sun, 02 Jan 2022 22:08:57 +0100

We continue to design. According to the previous section, we have designed birds and pipes. The rest is scoring and collision monitoring. The following is the design one by one.

According to the game assumption, when the bird flies over the pipe, the player's score is increased by 1 Here, the logic of flying over the pipeline is simplified: when the pipeline is moved to a certain distance on the left side of the window, the default is that the bird flies over the pipeline, so that the score is increased by 1 and displayed on the screen. This function has been implemented in the updatePipeline() method. The code is as follows:

import pygame
import sys
import random

class Bird(object):
    """Define a bird"""
    def __init__(self):
        """"Define initialization method"""
        self.birdRect = pygame.Rect(65, 50, 50, 50)  # Bird rectangle
        # Define a list of 3 states for birds
        self.birdStatus = [pygame.image.load("assets/1.png"),
                           pygame.image.load("assets/2.png"),
                           pygame.image.load("assets/dead.png")]
        self.status = 0
        self.birdX = 120
        self.birdY = 350
        self.jump = False
        self.jumpSpeed = 10
        self.gravity = 5
        self.dead = False
    def birdUpdate(self):
        if self.jump:
            self.jumpSpeed-=1
            self.birdY-=self.jumpSpeed
        else:
            self.gravity+=0.2
            self.birdY+=self.gravity
        self.birdRect[1]=self.birdY

class Pipeline(object):
    """Define a pipe class"""
    def __init__(self):
        """Define initialization method"""
        self.wallx=400
        self.pineUp=pygame.image.load("assets/top.png")
        self.pineDown=pygame.image.load("assets/bottom.png")
    def updatePipeline(self):
        """Horizontal movement"""
        self.wallx-=5
        #When the pipeline runs to a certain position, that is, the bird flies over the pipeline, the score is increased by 1, and the pipeline is reset
        if self.wallx<-80:
            global score
            score+=1
            self.wallx=400

def createMap():
    """Define how to create a map"""
    screen.fill((255,255,255))     #fill color
    screen.blit(background,(0,0))  #Fill in background
    #Show pipe
    screen.blit(Pipeline.pineUp,(Pipeline.wallx,-300))
    screen.blit(Pipeline.pineDown, (Pipeline.wallx, 500))
    Pipeline.updatePipeline()
    if Bird.dead:
        Bird.status=2
    elif Bird.jump:
        Bird.status=1
    screen.blit(Bird.birdStatus[Bird.status],(Bird.birdX,Bird.birdY))
    Bird.birdUpdate()
    #Show score
    screen.blit(font.render(str(score),-1,(255,255,255)),(200,50))
    pygame.display.update()        #update display
if __name__=='__main__':
    """main program"""
    pygame.init()                 #Initialize pygame
    pygame.font.init()
    font=pygame.font.SysFont(None,50)#Set default font and size
    size=width,height=400,680     #Settings window
    screen=pygame.display.set_mode(size)  #Display window
    clock=pygame.time.Clock()     #set clock
    Pipeline=Pipeline()           #Instantiate pipe class
    Bird=Bird()                   #Instantiated bird
    score=0
    while True:
        clock.tick(60)            #Execute 60 times per second
        for event in pygame.event.get():
            if event.type==pygame.QUIT:
                sys.exit()
            if (event.type==pygame.KEYDOWN or event.type==pygame.MOUSEBUTTONDOWN)\
                and not Bird.dead:
                Bird.jump=True
                Bird.gravity=5
                Bird.jumpSpeed=10
        background=pygame.image.load("assets/background.png")  #Load background picture
        createMap()               #draw a map
    pygame.quit()                 #sign out

The operation results are as follows:

The operation effect at this time is that when the pipeline moves to the left and disappears in the canvas, a score will be added. However, at present, due to the lack of setting of the bird killing mechanism, when the bird is no longer controlled and falls outside the canvas, the score is still increasing.

So let's improve this function, add collision monitoring, and control the end of the game.

According to the assumption, when the bird collides with the pipe, the bird color changes to gray, the game ends, and the total score is displayed,. In the checkDead() function, you can obtain the rectangular area object of the bird and the rectangular area object of the pipe respectively through pygame.Rect(). The object has a colliderect() method to judge whether the two rectangular areas collide. In case of collision, set bird The dead property is True. In addition, when the form is deleted, bird.com is also set The dead property is True. Finally, the total score is displayed in two lines of text. The code is as follows:

# encoding:utf-8
import pygame
import sys
import random

class Bird(object):
    """Define a bird"""
    def __init__(self):
        """"Define initialization method"""
        self.birdRect = pygame.Rect(65, 50, 50, 50)  # Bird rectangle
        # Define a list of 3 states for birds
        self.birdStatus = [pygame.image.load("assets/1.png"),
                           pygame.image.load("assets/2.png"),
                           pygame.image.load("assets/dead.png")]
        self.status = 0
        self.birdX = 120
        self.birdY = 350
        self.jump = False
        self.jumpSpeed = 10
        self.gravity = 5
        self.dead = False
    def birdUpdate(self):
        if self.jump:
            self.jumpSpeed-=1
            self.birdY-=self.jumpSpeed
        else:
            self.gravity+=0.2
            self.birdY+=self.gravity
        self.birdRect[1]=self.birdY

class Pipeline(object):
    """Define a pipe class"""
    def __init__(self):
        """Define initialization method"""
        self.wallx=400
        self.pineUp=pygame.image.load("assets/top.png")
        self.pineDown=pygame.image.load("assets/bottom.png")
    def updatePipeline(self):
        """Horizontal movement"""
        self.wallx-=5
        #When the pipeline runs to a certain position, that is, the bird flies over the pipeline, the score is increased by 1, and the pipeline is reset
        if self.wallx<-80:
            global score
            score+=1
            self.wallx=400

def createMap():
    """Define how to create a map"""
    screen.fill((255,255,255))     #fill color
    screen.blit(background,(0,0))  #Fill in background
    #Show pipe
    screen.blit(Pipeline.pineUp,(Pipeline.wallx,-300))
    screen.blit(Pipeline.pineDown, (Pipeline.wallx, 500))
    Pipeline.updatePipeline()
    if Bird.dead:
        Bird.status=2
    elif Bird.jump:
        Bird.status=1
    screen.blit(Bird.birdStatus[Bird.status],(Bird.birdX,Bird.birdY))
    Bird.birdUpdate()
    #Show score
    screen.blit(font.render(str(score),-1,(255,255,255)),(200,50))
    pygame.display.update()        #update display
def checkDead():
    # Rectangular position of upper tube
    upRect = pygame.Rect(Pipeline.wallx,-300,
                         Pipeline.pineUp.get_width() - 10,
                         Pipeline.pineUp.get_height())

    # Rectangular position of the lower tube
    downRect = pygame.Rect(Pipeline.wallx,500,
                           Pipeline.pineDown.get_width() - 10,
                           Pipeline.pineDown.get_height())
    # Check whether the bird collides with the upper and lower pipes
    if upRect.colliderect(Bird.birdRect) or downRect.colliderect(Bird.birdRect):
        Bird.dead = True
    # Check whether the bird flies out of the upper and lower boundaries
    if not 0 < Bird.birdRect[1] < height:
        Bird.dead = True
        return True
    else :
        return False

def getResultl():
    final_text1="Game Over!"
    u="your final score is:"+str(score)

    ft1_font=pygame.font.SysFont("Arial",70)
    ft1_surf=font.render(final_text1,1,(242,3,35))  #Sets the color of the first line of text
    ft2_font = pygame.font.SysFont("Arial", 50)
    ft2_surf = font.render(u, 1, (242, 177, 8))  # Sets the color of the second line of text
    #Set the display position of the first line of text
    screen.blit(ft1_surf,[screen.get_width()/2-ft1_surf.get_width()/2,100])
    # Set the display position of the second line of text
    screen.blit(ft2_surf, [screen.get_width() / 2 - ft2_surf.get_width() / 2, 200])
    pygame.display.flip() #Update the entire Surface object to be displayed to the screen
if __name__=='__main__':
    """main program"""
    pygame.init()                 #Initialize pygame
    pygame.font.init()
    font=pygame.font.SysFont(None,50)#Set default font and size
    size=width,height=400,680     #Settings window
    screen=pygame.display.set_mode(size)  #Display window
    clock=pygame.time.Clock()     #set clock
    Pipeline=Pipeline()           #Instantiate pipe class
    Bird=Bird()                   #Instantiated bird
    score=0
    while True:
        clock.tick(60)            #Execute 60 times per second
        for event in pygame.event.get():
            if event.type==pygame.QUIT:
                sys.exit()
            if (event.type==pygame.KEYDOWN or event.type==pygame.MOUSEBUTTONDOWN)\
                and not Bird.dead:
                Bird.jump=True
                Bird.gravity=5
                Bird.jumpSpeed=10
        background=pygame.image.load("assets/background.png")  #Load background picture
        if checkDead():
            getResultl()
        else:
            createMap()   #draw a map
    pygame.quit()                 #sign out

Final operation effect:

At this time, the design of Flappy Bird is completed. The bird is considered dead when it collides with the pipe and leaves the screen, and then the game is over.

The problem of Chinese garbled code has not been solved here for the time being. It has been set to the encoding format of utf-8, but I don't know what's going on. It still displays garbled code. If it is solved, I will write an article about solving Python Chinese garbled code again. Please pay attention.

 

 

Topics: Python pygame