본문 바로가기

Python/Python 초등 교육

11. 장애물 넘기 게임 - 4부

반응형

이번시간에는 속도에 개념에 대해 알아 보려고 했는데 그전에 공룡을 뛰게 만들고 점프고 하게 만들어 보는것을 먼저 하고 

장애물과 공룡의 움직임에 속도의 개념을 넣어 보는것이 좋을것 같아요.

 

이제 장애물이 움직이게 했으니까 공룡을 뛰게 만들어 보아요. 

공룡을 뛰게 만든다는건 우리 눈에 보이는 모습인것이고, 실제는 공룡의 왼발 이미지와  , 오른발 이미지가 번갈아가면서 보여지게 되면

뛰는것처럼 보이게됩니다. 

 

그래서 준비해야하는 이미지는 아래와 같은 이미지에요.

dino1.png
dino2.png

위 뒤개의 이미지가 번갈아 가면서 움직이게 되는것이죠. 위 이미지는 https://github.com/devraccon/PracticeGame1/tree/master/images (요기 링크에서 다운 받으실수 있어요)

 

이렇게 두개의 이미지가 준비 되었다면 우리가 처음 보여지게 했던 공룡 이미지 dino1.png 를 dino2.png를 어떻게 번갈아 가면서 보여지게 할지를 고민해 봐야 해요.  어떻게 하면 좋을까요? 실제 개발자들은 이런 모습들을 프로그램으로 어떻게 자연스럽게 보여지게 만들까를 고민 하고 있어요. 여러분도 같이 고민해 보아요.

 

단순하죠? dino1.png -> dino2.png -> dino1.png .... (반복) 이렇게 하면 되겠죠? 그럼 생각했던 모습으로 코딩해 보아요.

반복을 하게 만드는 시점이 언제여야 할까요? 맞아요 .한 프레임 마다 반복을 하면 됩니다. 애니메이션을 볼때 우리는 움직이는것처럼 보이지만 실제 애니메이션 제작은 한장면 한장명을 연결해서 이어붙이는 방식으로 제작이 됩니다. (동영상도 마찬가지에요)

 

그래서 우리가 앞에서 fps 즉 프레임의 개념을 배운거에요.  

    while True:
        tick = fps.tick(30)
        ....
        pygame.display.update()

 

앞에서 작성했던 코드를 다시 한번 복습해 보면 . 위코드는 초당 30번 게임화면을 갱신하겠다 즉 , 1초에 30장의 이미지를 보여주겠다라는 뜻과 같아요. 이말은 공룡이 왼발 오른발을 번갈아 움직이게 하는게 초당 30번 번걸아 움직이게 된다는 말이되는것죠? 

 

그럼 우리는 공룡 이미지를 바꿔줘야하는데 언제 바꿔야 줘야 할까요? 맞아요!! 바로 저기 while문에 변경되게 해주어야 합니다

#공룡 이미지 로드
image_dino1 = pygame.image.load("images/dino1.png")
image_dino2 = pygame.image.load("images/dino2.png")

공룡 이미지를 두개다 먼저 로드 해 놓았어요. 그리고 while문 안에서 프레임이 바뀔떄 마다 두개의 이미지를 번갈아 보여주게 만들거에요.

 

 leg_swap = True  
 while True:
    tick = fps.tick(30)
    check_time = check_time+1
    print("time : ", datetime.now(), "초당 frame 수 :", check_time)
    screen.fill((255, 255, 255))
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            pygame.quit()
            sys.exit()
    #공룡이미지를 화면에 나오게 하는 부분 , dino_x , dino_y 좌표에 나오게됨
    if leg_swap:
        screen.blit(image_dino1, (dino_x, dino_y))
        leg_swap = False
    else:
        screen.blit(image_dino2, (dino_x, dino_y))
        leg_swap = True

    #장애물의 x 위치값을 화면이 한번 깜빡일때 마다 tree_move_by_tick만큼 왼쪽으로 이동
    #왼쪽으로 이동은 x값이 작아지게 만들어야 하니까 원래 장애물의 위치에서 계속 minus를 해준다.
    tree_x = tree_x - tree_move_by_tick
    #장애물나무의 위치를 설정해서 화면에 나오게 함.
    screen.blit(image_tree, (tree_x, tree_y))
    pygame.display.update()

요런 형태가 되게 되겠죠? 한번 왼발 했으면 다음은 오른발 이미지를 보여주어야 하기때문에 leg_swap이라는 변수를 사용했습니다.

이런 형태의 변수를 굉장히 많이 사용하게 될거에요. 변수아 사용 방법에 대해 잘 기억애 두어야 합니다.

 

import sys
import pygame
from datetime import datetime

pygame.init()
pygame.display.set_caption("데브라쿤 파이썬게임 연습1")
MAX_WIDTH = 800
MAX_HEIGHT = 400

def main():
    # 게임 화면의 사이즈 설정
    screen = pygame.display.set_mode((MAX_WIDTH, MAX_HEIGHT))

    # #공룡 이미지 로드
    image_dino1 = pygame.image.load("images/dino1.png")
    image_dino2 = pygame.image.load("images/dino2.png")
    leg_swap = True
    dino_height = image_dino1.get_size()[1]
    # 공룡이 바닥에 붙어 있는 모양을 만들고 싶음
    dino_bottom = MAX_HEIGHT - dino_height

    # 공룡 좌표
    dino_x = 50
    dino_y = dino_bottom

    image_tree = pygame.image.load("images/tree.png")
    # 화면의 제일 우측에 장애물을 위치하게 해준다.
    tree_height = image_tree.get_size()[1]
    tree_x = MAX_WIDTH - 30
    tree_y = MAX_HEIGHT - tree_height

    tree_move_by_tick = 5
    # 게임 화면의 프레임 설정 ( 1초의 몇번을 깜빡일것인가)
    fps = pygame.time.Clock()
    check_time = 0

    while True:
        tick = fps.tick(30)
        check_time = check_time+1
        print("time : ", datetime.now(), "초당 frame 수 :", check_time)
        screen.fill((255, 255, 255))
        for event in pygame.event.get():
            if event.type == pygame.QUIT:
                pygame.quit()
                sys.exit()
        #공룡이미지를 화면에 나오게 하는 부분 , dino_x , dino_y 좌표에 나오게됨
        if leg_swap:
            screen.blit(image_dino1, (dino_x, dino_y))
            leg_swap = False
        else:
            screen.blit(image_dino2, (dino_x, dino_y))
            leg_swap = True

        #장애물의 x 위치값을 화면이 한번 깜빡일때 마다 tree_move_by_tick만큼 왼쪽으로 이동
        #왼쪽으로 이동은 x값이 작아지게 만들어야 하니까 원래 장애물의 위치에서 계속 minus를 해준다.
        tree_x = tree_x - tree_move_by_tick
        #장애물나무의 위치를 설정해서 화면에 나오게 함.
        screen.blit(image_tree, (tree_x, tree_y))
        pygame.display.update()

if __name__ == '__main__':
    main()

 최종적으로 위와 같은 형태의 코드가 될거에요. 이제 게임 실행해 봅시다. 

위와 같이 공룡이 뛰는 모습이 되었습니다.  자 이제 공룡을 점프하게 만들어 볼까요?

간단해요 점프라는게 뭘까요? 간단하게 좌표에서 Y 값 즉 세로 값이 바뀐다고 생각하면 쉬워요.

 

앞에서 좌표를 설명할때 왼쪽 상단 모서리 부분이  가로 0 , 세로  0 ,즉  x 좌표 0 , y 좌표 0 (앞으로  0 ,0 으로 표기 할게요) 

세로는 아래로 내려 올수록 숫자가 커지고 ,  가로는 오른쪽으로 갈수록 숫자가 커지게 됩니다. 

 

그럼 공룡이 점프하게 하려면 어떻게 해야 할까요? 네 ! 공룡의 Y 좌표값을 줄여주면 되요. 어디까지 줄여야 할까요? 

우리가 원하는 위치가 올라갔다면 다시 원래 위치로 내려 와야겠죠?

is_jumping = False
max_jumping_height = dino_bottom - 120

while True:
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            pygame.quit()
            sys.exit()
        elif event.type == pygame.KEYUP:
            if not is_jumping:
                is_jumping = True
    if is_jumping:
        dino_y = dino_y - 10
        if dino_y <= max_jumping_height:
            is_jumping = False
    else:
        dino_y = dino_y + 10
        if dino_y >= dino_bottom:
            dino_y = dino_bottom
  • is_jumping :
    • 이변수는 현재 공룡이 점프중인지를 체크하기 위한 변수에요. 점프키를 눌렀을때 공룡이 점프를 할텐데  이때 우리가 원하는 위치까지 점프한 공룡이 점프를 멈추가 다시 내려오게 만드는 용도로 쓰이게 됩니다.
  • max_jumping_height : 
    • 공룡의 최대 점프 높이를 담아 놓은 변수에요. 
  • event_type == pygame.KEYUP :
    • 현재 어떤 키를 눌러서 땠을때 공룡의 점프 변수값을 변경해주고 있어요. 원하는 특정키로 바꿀수 있으니 여러분이 원하는 키를 바꿔서 사용해 봅시다. 
if is_jumping:
    dino_y = dino_y - 10
    if dino_y <= max_jumping_height:
        is_jumping = False
else:
    dino_y = dino_y + 10
    if dino_y >= dino_bottom:
        dino_y = dino_bottom

이부분은 설명은 앞에서도 했어요. 공룡이 점프중 즉 아직 우리가 원하는 점프 최대 높이까지 올려갈때까지 공룡은 계속 점프중인 상태이고 

이때 한프레임마다 공룡은 위로 10씩 움직이게 됩니다. ( 여기서  10을 변경해 보도록 합시다. 이 값에 따라 점프하는 속도가 달라져요)

그리고 우리가 원하는 높이까지 올라 갔다면 공룡은 점프를 멈추게 되고 다시 원래 위치까지 10씩 내려오게 됩니다. 

 

요기까지 하고 실행을 해보아요.

import sys
import pygame
from datetime import datetime

pygame.init()
pygame.display.set_caption("데브라쿤 파이썬게임 연습1")
MAX_WIDTH = 800
MAX_HEIGHT = 400

def main():
    # 게임 화면의 사이즈 설정
    screen = pygame.display.set_mode((MAX_WIDTH, MAX_HEIGHT))

    # #공룡 이미지 로드
    image_dino1 = pygame.image.load("images/dino1.png")
    image_dino2 = pygame.image.load("images/dino2.png")

    dino_height = image_dino1.get_size()[1]
    # 공룡이 바닥에 붙어 있는 모양을 만들고 싶음
    dino_bottom = MAX_HEIGHT - dino_height
    leg_swap = True
    is_jumping = False
    max_jumping_height = dino_bottom - 120

    # 공룡 좌표
    dino_x = 50
    dino_y = dino_bottom

    image_tree = pygame.image.load("images/tree.png")
    # 화면의 제일 우측에 장애물을 위치하게 해준다.
    tree_height = image_tree.get_size()[1]
    tree_x = MAX_WIDTH - 30
    tree_y = MAX_HEIGHT - tree_height

    tree_move_by_tick = 5
    # 게임 화면의 프레임 설정 ( 1초의 몇번을 깜빡일것인가)
    fps = pygame.time.Clock()
    check_time = 0

    while True:
        tick = fps.tick(30)
        check_time = check_time+1
        print("time : ", datetime.now(), "초당 frame 수 :", check_time)
        screen.fill((255, 255, 255))
            for event in pygame.event.get():
                if event.type == pygame.QUIT:
                    pygame.quit()
                    sys.exit()
                elif event.type == pygame.KEYUP:
                    if not is_jumping:
                        is_jumping = True
        #공룡이미지를 화면에 나오게 하는 부분 , dino_x , dino_y 좌표에 나오게됨
        if leg_swap:
            screen.blit(image_dino1, (dino_x, dino_y))
            leg_swap = False
        else:
            screen.blit(image_dino2, (dino_x, dino_y))
            leg_swap = True

        if is_jumping:
            dino_y = dino_y - 10
            if dino_y <= max_jumping_height:
                is_jumping = False
        else:
            dino_y = dino_y + 10
            if dino_y >= dino_bottom:
                dino_y = dino_bottom


        #장애물의 x 위치값을 화면이 한번 깜빡일때 마다 tree_move_by_tick만큼 왼쪽으로 이동
        #왼쪽으로 이동은 x값이 작아지게 만들어야 하니까 원래 장애물의 위치에서 계속 minus를 해준다.
        tree_x = tree_x - tree_move_by_tick
        #장애물나무의 위치를 설정해서 화면에 나오게 함.
        screen.blit(image_tree, (tree_x, tree_y))
        pygame.display.update()

if __name__ == '__main__':
    main()

 

위와 같은 공룡이 점프를 하는 모습이 완성 되었습니다.

이제 조금씩 모양이 완성 되어 있는 모습을 보니 뿌듯하네요. 이제 공룡과 장애물에 속도를 넣어 주고 

좀 더 게임 다운 모습을 만들어 보아요.